注册 登录  
 加关注
   显示下一条  |  关闭
温馨提示!由于新浪微博认证机制调整,您的新浪微博帐号绑定已过期,请重新绑定!立即重新绑定新浪微博》  |  关闭

Koala++'s blog

计算广告学 RTB

 
 
 

日志

 
 

Lucene源代码分析[5]  

2009-07-02 16:18:33|  分类: Lucene |  标签: |举报 |字号 订阅

  下载LOFTER 我的照片书  |

         我们再看没有看完的DocumentWriter中的addDocument函数:

// write field values

FieldsWriter fieldsWriter = new FieldsWriter(directory, segment,

       fieldInfos);

    看一下这个函数FieldWriter类构造函数:

FieldsWriter(Directory d, String segment, FieldInfos fn) throws

IOException {

    fieldInfos = fn;

    fieldsStream = d.createOutput(segment + ".fdt");

    indexStream = d.createOutput(segment + ".fdx");

}

    引用一下[邱哲,符滔滔].fdt.fdx是综合使用的两个文件,其中.fdt类型文件用于存储具有Store.YESField数据,而.fdx类型文件则是一个索引,用于存储Document.fdt中的位置。

    好了,我们再看一下重要的函数:

fieldsWriter.addDocument(doc);

    还是比较长的,但是直接列出来算了:

final void addDocument(Document doc) throws IOException {

    indexStream.writeLong(fieldsStream.getFilePointer());

 

    int storedCount = 0;

    Enumeration fields = doc.fields();

    while (fields.hasMoreElements()) {

        Field field = (Field) fields.nextElement();

        if (field.isStored())

            storedCount++;

    }

    fieldsStream.writeVInt(storedCount);

 

    fields = doc.fields();

    while (fields.hasMoreElements()) {

        Field field = (Field) fields.nextElement();

        if (field.isStored()) {

            fieldsStream.writeVInt(fieldInfos.fieldNumber(

field.name()));

 

            byte bits = 0;

            if (field.isTokenized())

                bits |= FieldsWriter.FIELD_IS_TOKENIZED;

            if (field.isBinary())

                bits |= FieldsWriter.FIELD_IS_BINARY;

            if (field.isCompressed())

                bits |= FieldsWriter.FIELD_IS_COMPRESSED;

           

            fieldsStream.writeByte(bits);

           

            if (field.isCompressed()) {

              // compression is enabled for the current field

              byte[] data = null;

              // check if it is a binary field

              if (field.isBinary()) {

                data = compress(field.binaryValue());

              }

              else {

                data = compress(field.stringValue().getBytes("UTF-8"));

              }

              final int len = data.length;

              fieldsStream.writeVInt(len);

              fieldsStream.writeBytes(data, len);

            }

            else {

              // compression is disabled for the current field

              if (field.isBinary()) {

                byte[] data = field.binaryValue();

                final int len = data.length;

                fieldsStream.writeVInt(len);

                fieldsStream.writeBytes(data, len);

              }

              else {

                fieldsStream.writeString(field.stringValue());

              }

            }

        }

    }

}

    我们看到第一句就是在.fdx中写加当前.fdt的位置,writeLong太简单了,就是分成两个int写入,不列出代码了,第二步是我们把要保存的Field数一下,保存起来。再下来就是把是第几个Field写进去,再下来是把是不是分词,用二进制形式,是否压缩之类的用一个Byte保存,再把Field中的内容写进文件中。

    我们这里既不是Compressed也不是Binary,所以我也不想介绍writeByteswriteString我们看过了。

    .fdx.fdt的内容列出来:

00 00 00 00 00 00 00 00

01 00 01 0B 68 65 6C 6C 6F 20 77 6F 72 6C 64

    .fdx中的内容很简单因为我们就保存了一个域,所以值为0long8个字节。我们看.fdt中,01是有多少个域要保存,只有一个,第二个00是第几个Field,是第0个,第三个01是表示被索引而不且二进制和压缩。0B11,表示hello world的长度,后面内容就是hello world字符串了。

    太简单了,也看不出来什么,把测试程序换一下:

package forfun;

 

import org.apache.lucene.analysis.SimpleAnalyzer;

import org.apache.lucene.document.Document;

import org.apache.lucene.document.Field;

import org.apache.lucene.index.IndexWriter;

 

public class FieldTest

{

    public static void main( String[] args ) throws Exception

    {

       IndexWriter writer = new IndexWriter( "E:\\a\\", new

 SimpleAnalyzer(), true);

        writer.setUseCompoundFile( false );

      

       Document doc1 = new Document();

       Field name = new Field( "TheField", "hello world",

           Field.Store.YES, Field.Index.TOKENIZED );

       doc1.add( name );

      

       Document doc2 = new Document();

       Field nom = new Field( "LeDomaine", "bonjour monde",

              Field.Store.YES, Field.Index.TOKENIZED );

       doc2.add( nom );

   

       writer.addDocument( doc1 );

       writer.addDocument( doc2 );

       writer.close();

    }

}

    加入两个文档,两个域,.fdx.fdt中的内容为:

00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0F

01 00 01 0B 68 65 6C 6C 6F 20 77 6F 72 6C 64 01

01 01 0D 62 6F 6E 6A 6F 75 72 20 6D 6F 6E 64 65

.fdx中第一个值为0,第二个值为15。在.fdt中用红字标出来的就是第15个值,也就是第二个doc开始的位置。其它的也没什么变化。

 

 

 

 

 

 

 

 

  评论这张
 
阅读(1128)| 评论(0)
推荐 转载

历史上的今天

评论

<#--最新日志,群博日志--> <#--推荐日志--> <#--引用记录--> <#--博主推荐--> <#--随机阅读--> <#--首页推荐--> <#--历史上的今天--> <#--被推荐日志--> <#--上一篇,下一篇--> <#-- 热度 --> <#-- 网易新闻广告 --> <#--右边模块结构--> <#--评论模块结构--> <#--引用模块结构--> <#--博主发起的投票-->
 
 
 
 
 
 
 
 
 
 
 
 
 
 

页脚

网易公司版权所有 ©1997-2017