由两个文件组成正向文档信息
1. 正向文档指针(.fdx文件)
2. 正向文档内容(.fdt文件)
正向文档的索引过程
l 涉及两个类
1. FieldInfos *fieldInfos;(字段信息:例如字段名,字段属性等)
2. FieldsWriter *fieldsWriter;(正向文档读写器)
l 索引过程分两部分
1. 构建部分
2. 合并部分
一、索引构建过程
//当添加文档时,调用以下addDocument(注意:每次添加文档都重复生成DocumentWriter对象,颇为浪费)函数,涉及到正向文档的主要有两块
void DocumentWriter::addDocument(const char* segment, Document* doc)
{
…………………..
// 其他过程暂时略过
1. 字段信息
// 遍历文档,添加字段信息
// 注意,如果每次构建的文档结构一样,那么此过程便一再重复了
fieldInfos = _CLNEW FieldInfos();
fieldInfos->add(doc);
const char* buf = Misc::segmentname(segment, ".fnm");
fieldInfos->write(directory, buf);
………….
2. 正向文档内容
// write field values
//FieldsWriter fieldsWriter(directory, segment, fieldInfos);
// 写入字段内容
//try
//{
// add by lxp
//fieldsWriter.addDocument(doc);
//} _CLFINALLY( fieldsWriter.close() );
……..
}
fieldInfos->add(doc);此过程功能是
1. 统计字段的属性(例如是否存储/索引/分词)
2. 建立一个映射表:字符串和数值;一一对应。可由数值查知字段名,可由字段名得知字段数值
fieldsWriter.addDocument(doc);此过程功能是
1. 遍历所有需要存储的字段,将索引信息写入磁盘(缓存)
2. 先写入正向文档的偏移值(.fdx)
3. 写入需要存储的字段个数(fieldsStream->writeVInt(storedCount);)
4. 重复以下过程
l 写入一个uint_8的该字段属性值(fieldsStream->writeByte(bits);)
l 写入字段内容(可选多种方式写入:例如是否压缩,是否二进制流)
二、合并过程
索引合并时调用int32_t SegmentMerger::mergeFields()过程合并字段内容
{
for (uint32_t i = 0; i < readers.size(); i++) {
//get the i-th reader
reader = readers[i];
//通过计算fdt文件大小得知此段内的文档数
// (int32_t)indexStream->length()/8;
int32_t maxDoc = reader->maxDoc();
Iterate through all the documents managed by the current reader
//for (int32_t j = 0; j < maxDoc; j++)
//{
// //Check if the j-th document has been deleted, if so skip it
// if (!reader->isDeleted(j))
// {
// //Get the document
// if ( reader->document(j, &doc) ) //取出正向文档
// {
// //Add the document to the new FieldsWriter
// fieldsWriter->addDocument( &doc );//重新写入
// docCount++;
// //doc is cleard for re-use
// doc.clear();
// }
// }
//}
}
}
三、优化过程
由IndexWriter控制正向文档的读写
1. 字段信息一次统计(因文档结构一样),由IndexWriter控制下的IndexWriter::fieldInfos
2. 正向文档一直末尾添加,不重读入,不重写入
为此
l 索引时将正向文档的读写交给IndexWriter控制下的读写器
IndexWriter:: fieldsWriter写入,每次追尾
l 合并过程不执行mergeFields()->//mergeFields();
l 合并过程中需要的字段信息由始至终使用IndexWriter::fieldInfos
l 合并过程中需要的文档数统计由SegmentInfo* si取得