Пример #1
0
/*****************************************************************************
*  function name : Buiding
*  params :
*  return :
*
*  description : 构建索引文件,并将detail存入redis中,这个函数太啰嗦了。
*
******************************************************************************/
func (this *DBBuilder) Buiding() error {

	var fields string
	for index, v := range this.Fields {
		//构造sql语句
		fields = fields + "," + v.Name

		//新建插件
		cumstom := plugins.NewPlus(v.Name)
		cumstom.Init()

		//构造索引数据指针
		if v.IsIvt {
			if v.FType == "T" {
				this.Fields[index].IvtIdx = utils.NewInvertIdx(utils.TYPE_TEXT, v.Name)
				this.Fields[index].IvtStrDic = utils.NewStringIdxDic(v.Name)
				this.Fields[index].CustomeInter = cumstom

			}

			if v.FType == "N" {

				this.Fields[index].IvtIdx = utils.NewInvertIdx(utils.TYPE_NUM, v.Name)
				this.Fields[index].IvtNumDic = utils.NewNumberIdxDic(v.Name)
				this.Fields[index].CustomeInter = cumstom
			}

			if v.FType == "I" {

				this.Fields[index].IvtIdx = utils.NewInvertIdx(utils.TYPE_TEXT, v.Name)
				this.Fields[index].IvtStrDic = utils.NewStringIdxDic(v.Name)
				this.Fields[index].CustomeInter = cumstom

			}

		}

		if v.IsPlf {
			if v.FType == "T" {
				this.Fields[index].PlfText = indexer.NewTextProfile(v.Name)
				this.Fields[index].PlfText.SetCustomInterface(cumstom)
			}

			if v.FType == "N" {
				this.Fields[index].PlfNumber = indexer.NewNumberProfile(v.Name)
				this.Fields[index].PlfNumber.SetCustomInterface(cumstom)
			}

			if v.FType == "I" {
				this.Fields[index].PlfByte = indexer.NewByteProfile(v.Name)
				this.Fields[index].PlfByte.SetCustomInterface(cumstom)
			}

		}

	}
	//fmt.Printf("%v\n", fields)

	this.DetailIdx = indexer.NewDetail()

	sql := fmt.Sprintf(this.sql, fields[1:len(fields)])
	fmt.Printf("SQL :: %v \n", sql)

	rows, err := this.Dbadaptor.QueryFormat(sql)
	if err != nil {
		this.Logger.Error(" %v", err)
		return err
	}
	defer rows.Close()
	var doc_id int64
	doc_id = 1
	segment := utils.NewSegmenter("./data/dictionary.txt")
	builder := &utils.IndexBuilder{Segmenter: segment, TempIndex: make(map[string][]utils.TmpIdx), TempIndexNum: make(map[string]int64)}

	for rows.Next() {
		//values := make([]interface{},len(this.Fields))
		values := make([]interface{}, len(this.Fields))
		writeCols := make([]string, len(this.Fields))
		for i, _ := range writeCols {
			values[i] = &writeCols[i]
		}

		err := rows.Scan(values...)
		if err != nil {
			this.Logger.Error("SQL ERROR : %v", err)
			return err
		}
		redis_map := make(map[string]string)
		for index, v := range writeCols {
			redis_map[this.Fields[index].Name] = v
			//v,_ := value.(string)
			if this.Fields[index].IsIvt {

				if this.Fields[index].FType == "T" || this.Fields[index].FType == "I" {
					err := builder.BuildTextIndex(doc_id, v, this.Fields[index].IvtIdx, this.Fields[index].IvtStrDic, this.Fields[index].SType, false, this.Fields[index].CustomeInter)
					//err := builder.BuildTextIndexTemp(doc_id, v, this.Fields[index].IvtIdx, this.Fields[index].IvtStrDic,this.Fields[index].SType,this.Fields[index].Name)
					if err != nil {
						this.Logger.Error("ERROR : %v", err)
					}
				}

				if this.Fields[index].FType == "N" {
					v_num, err := strconv.ParseInt(v, 0, 0)
					if err != nil {
						v_num = 0
						//this.Logger.Warn("Warning : name : [%v] , value: [%v] , error : [%v]", this.Fields[index].Name, v, err)
					}

					err = builder.BuildNumberIndex(doc_id, v_num, this.Fields[index].IvtIdx, this.Fields[index].IvtNumDic, this.Fields[index].SType, false, this.Fields[index].CustomeInter)
					//err = builder.BuildNumberIndexTemp(doc_id, v_num, this.Fields[index].IvtIdx, this.Fields[index].IvtNumDic,this.Fields[index].Name)
					if err != nil {
						this.Logger.Error("ERROR : %v", err)
					}
				}

			}

			if this.Fields[index].IsPlf {

				if this.Fields[index].FType == "T" {
					//添加日期类型的更新,仅精确到天 add by wuyinghao 2015-08-21
					if this.Fields[index].SType == 5 {
						vl := strings.Split(v, " ")
						v = vl[0]
					} else if this.Fields[index].SType == 9 {
						v = this.Fields[index].PlfText.GetCustomInterface().BuildStringProfile(v)
					}
					err := this.Fields[index].PlfText.PutProfile(doc_id, v)
					if err != nil {
						this.Logger.Error("ERROR : %v", err)
					}
				}

				if this.Fields[index].FType == "N" {
					v_num, err := strconv.ParseInt(v, 0, 0)
					if err != nil {
						v_num = 0
						//this.Logger.Warn("Warning : name : %v , value: %v , error : %v", this.Fields[index].Name, v, err)
					}
					if this.Fields[index].SType == 9 {
						v_num = this.Fields[index].PlfNumber.GetCustomInterface().BuildIntProfile(v)
					}
					err = this.Fields[index].PlfNumber.PutProfile(doc_id, v_num)
					if err != nil {
						this.Logger.Error("ERROR : %v", err)
					}
				}

				if this.Fields[index].FType == "I" {
					v_byte := []byte(v)
					if this.Fields[index].SType == 9 {
						v_byte = this.Fields[index].PlfByte.GetCustomInterface().BuildByteProfile(v_byte)
					}
					err = this.Fields[index].PlfByte.PutProfile(doc_id, v_byte)
					if err != nil {
						this.Logger.Error("ERROR : %v", err)
					}
				}

			}

		}
		/////
		//this.RedisCli.SetFields(doc_id, redis_map)
		////
		//for k,v := range redis_map{
		//	fmt.Printf("\"%v\":\"%v\",",k,v)
		//}
		//fmt.Printf("\n")
		if this.DetailIdx.PutDocInfo(doc_id, redis_map) != nil {
			this.Logger.Error("PutDocInfo doc_id Error :  %v \n", err)
		}

		fieldlist := make([]string, 0)
		for k, _ := range redis_map {
			fieldlist = append(fieldlist, k)
		}

		doc_id++
		if doc_id%5000 == 0 {
			this.Logger.Info("processing doc_id :  %v \n", doc_id)
		}
		//this.Logger.Info("DOC_ID : %v  VALUE : %v", doc_id, writeCols)

	}

	writeCount := 0
	writeChan := make(chan string, 1000)

	this.DetailIdx.WriteDetailToFile()
	this.Logger.Info("Make BitMap File")
	utils.MakeBitmapFile()

	for index, _ := range this.Fields {
		if this.Fields[index].IsIvt {
			//utils.WriteToIndexFile(this.Fields[index].IvtIdx, fmt.Sprintf("./index/%v_idx.idx", this.Fields[index].Name))
			this.Fields[index].IvtIdx.WriteToFile()
			if this.Fields[index].FType == "T" || this.Fields[index].FType == "I" {

				this.Fields[index].IvtStrDic.WriteToFile()

			}

			if this.Fields[index].FType == "N" {
				this.Fields[index].IvtNumDic.WriteToFile()

			}

		}

		if this.Fields[index].IsPlf {

			if this.Fields[index].FType == "T" {

				this.Fields[index].PlfText.WriteToFile()

			}

			if this.Fields[index].FType == "N" {

				this.Fields[index].PlfNumber.WriteToFile()

			}

			if this.Fields[index].FType == "I" {

				this.Fields[index].PlfByte.WriteToFile()
				//go this.Fields[index].PlfByte.WriteToFileWithChan(writeChan)
				//writeCount++

			}

		}

	}

	//fmt.Printf("Waiting %v threads\n ", writeCount)
	if writeCount == 0 {
		close(writeChan)
		return nil
	}
	for {
		select {
		case file_name := <-writeChan:
			writeCount--
			fmt.Printf("Write [%v] finished \n ", file_name)
			if writeCount == 0 {
				fmt.Printf("Finish building all index...\n")
				close(writeChan)
				return nil
			}
		}
	}

	return nil

}
Пример #2
0
/*****************************************************************************
*  function name : InitIndexSet
*  params : 需要初始化的字段
*  return :
*
*  description : 根据配置文件初始化建立索引和正排的字段并读入内存中
*
******************************************************************************/
func (this *IndexSet) InitIndexSet(fields map[string]string, inc_field string) error {

	this.IncField = inc_field
	for k, v := range fields {

		var fi IndexFieldInfo
		err := json.Unmarshal([]byte(v), &fi)
		if err != nil {
			fmt.Printf("Unmarshal Error ...\n")
			return err
		}
		fi.Name = k
		this.FieldInfo[k] = &fi
		if this.FieldInfo[k].IsPK == true {
			this.PrimaryKey = k
		}
		cumstom := plugins.NewPlus(k)
		cumstom.Init()
		this.Logger.Info("========= Loading Index/Dictionary and Profile [ %v ] =========", k)
		if this.FieldInfo[k].IsIvt == true {
			idx := utils.NewInvertIdxWithName(k)
			this.Logger.Info("\t Loading Invert Index [ %v.idx.dic ] ", k)

			idx.ReadFromFile()
			if this.FieldInfo[k].FType == "T" || this.FieldInfo[k].FType == "I" { //text ivt

				dic := utils.NewStringIdxDic(k)
				this.Logger.Info("\t Loading Invert Index Dictionary [ %v.dic ] ", k)
				dic.ReadFromFile()

				index := NewTextIndex(k, idx, dic)
				index.SetCustomInterface(cumstom)
				this.PutIndex(k, index)

			} else if this.FieldInfo[k].FType == "N" { //number ivt

				dic := utils.NewNumberIdxDic(k)
				this.Logger.Info("\t Loading Invert Index Dictionary [ %v.dic ] ", k)
				dic.ReadFromFile()
				//dic.Display()
				index := NewNumberIndex(k, idx, dic)
				index.SetCustomInterface(cumstom)
				this.PutIndex(k, index)
			}

		}

		if this.FieldInfo[k].IsPlf == true {

			if this.FieldInfo[k].FType == "T" {

				pfl := NewTextProfile(k)
				this.Logger.Info("\t Loading Text Profile [ %v.pfl ] ", k)

				pfl.SetCustomInterface(cumstom)
				pfl.ReadFromFile()
				this.PutProfile(k, pfl)

			} else if this.FieldInfo[k].FType == "N" {

				pfl := NewNumberProfile(k)
				this.Logger.Info("\t Loading Number Profile [ %v.pfl ] ", k)

				pfl.SetCustomInterface(cumstom)
				pfl.ReadFromFile()

				this.PutProfile(k, pfl)
			} else if this.FieldInfo[k].FType == "I" {

				pfl := NewByteProfile(k)
				this.Logger.Info("\t Loading Byte Profile [ %v ] ", k)

				pfl.SetCustomInterface(cumstom)
				pfl.ReadFromFile()
				this.PutProfile(k, pfl)

			}
		}
	}

	//读取detail文件
	this.Logger.Info("Loading Detail idx .....")
	this.Detail = NewDetailWithFile()
	this.Detail.ReadDetailFromFile()
	//保存最大DocId
	this.MaxDocId = this.PflIndex[this.PrimaryKey].GetMaxDocId()

	return nil
}