![](/icons/13705yi.gif)
、 Lucene源码实现分析
![](/icons/13705de.gif)
介绍说明
通过以上对Lucene系统结构
![](/icons/13705de.gif)
分析
![](/icons/13705dou.gif)
我们已经大致
![](/icons/13705de.gif)
清楚了Lucene系统
![](/icons/13705de.gif)
组成
![](/icons/13705dou.gif)
以及在Lucene系统的上
![](/icons/13705de.gif)
开发步骤
![](/icons/13705dou2.gif)
接下来
![](/icons/13705dou.gif)
我们试图来分析Lucene项目(采用Lucene 1.2版本)
![](/icons/13705de.gif)
源码实现
![](/icons/13705dou.gif)
考察其实现
![](/icons/13705de.gif)
细节
![](/icons/13705dou2.gif)
这不仅仅是我们尝试用C
![](/icons/13705jiajia.gif)
语言重新实现Lucene
![](/icons/13705de.gif)
必须工作
![](/icons/13705dou.gif)
也是进
![](/icons/13705yi.gif)
步做Lucene开发工作
![](/icons/13705de.gif)
必要准备
![](/icons/13705dou2.gif)
因此
![](/icons/13705dou.gif)
这
![](/icons/13705yi.gif)
部分所涉及到
![](/icons/13705de.gif)
内容
![](/icons/13705dou.gif)
对于Lucene上
![](/icons/13705de.gif)
应用开发也是有价值
![](/icons/13705de.gif)
![](/icons/13705dou.gif)
尤其是本部分所做
![](/icons/13705de.gif)
文件格式分析
![](/icons/13705dou2.gif)
由于本文建立在我们
![](/icons/13705de.gif)
毕设项目的上
![](/icons/13705dou.gif)
且同时我们需要实现cLucene项目
![](/icons/13705dou.gif)
因此很遗憾
![](/icons/13705de.gif)
我们并没有完全
![](/icons/13705de.gif)
完成Lucene
![](/icons/13705de.gif)
所有源码实现
![](/icons/13705de.gif)
分析工作
![](/icons/13705dou2.gif)
接下来
![](/icons/13705de.gif)
部分
![](/icons/13705dou.gif)
我们将涉及
![](/icons/13705de.gif)
部分为Lucene文件格式分析
![](/icons/13705dou.gif)
Lucene中
![](/icons/13705de.gif)
存储抽象模块分析
![](/icons/13705dou.gif)
以及Lucene中
![](/icons/13705de.gif)
索引构建逻辑模块分析
![](/icons/13705dou2.gif)
这
![](/icons/13705yi.gif)
部分
![](/icons/13705dou.gif)
我们主要涉及到
![](/icons/13705de.gif)
是文件格式分析和存储抽象模块分析
![](/icons/13705dou2.gif)
2、 Lucene索引文件格式
在Lucene
![](/icons/13705de.gif)
web站点上
![](/icons/13705dou.gif)
有有关Lucene
![](/icons/13705de.gif)
文件格式
![](/icons/13705de.gif)
规范标准
![](/icons/13705dou.gif)
其规定了Lucene
![](/icons/13705de.gif)
文件格式采取
![](/icons/13705de.gif)
存储单位、组织结构、命名规范标准等等内容
![](/icons/13705dou.gif)
但是它仅仅是
![](/icons/13705yi.gif)
个规范标准介绍说明
![](/icons/13705dou.gif)
并没有从实现者角度来衡量这个规范标准
![](/icons/13705de.gif)
实现
![](/icons/13705dou2.gif)
因此
![](/icons/13705dou.gif)
我们以下
![](/icons/13705de.gif)
内容
![](/icons/13705dou.gif)
结合了我们自己
![](/icons/13705de.gif)
分析和文件格式
![](/icons/13705de.gif)
定义规范标准
![](/icons/13705dou.gif)
以期望给出
![](/icons/13705yi.gif)
个更加清晰
![](/icons/13705de.gif)
文件格式介绍说明
![](/icons/13705dou2.gif)
具体
![](/icons/13705de.gif)
文档规范标准可以参考后面
![](/icons/13705de.gif)
文献2
![](/icons/13705dou2.gif)
首先在Lucene
![](/icons/13705de.gif)
文件格式中
![](/icons/13705dou.gif)
以字节为基础
![](/icons/13705dou.gif)
定义了如下
![](/icons/13705de.gif)
数据类型:
表 3.1 Lucene文件格式中定义
![](/icons/13705de.gif)
数据类型
数据类型 所占字节长度(字节) 介绍说明
Byte 1 基本数据类型
![](/icons/13705dou.gif)
其他数据类型以此为基础定义
UInt32 4 32位无符号整数
![](/icons/13705dou.gif)
高位优先
UInt64 8 64位无符号整数
![](/icons/13705dou.gif)
高位优先
VInt 不定
![](/icons/13705dou.gif)
最少1字节 动态长度整数
![](/icons/13705dou.gif)
每字节
![](/icons/13705de.gif)
最高位表明还剩多少字节
![](/icons/13705dou.gif)
每字节
![](/icons/13705de.gif)
低 7位表明整数
![](/icons/13705de.gif)
值
![](/icons/13705dou.gif)
高位优先
![](/icons/13705dou2.gif)
可以认为值可以为无限大
![](/icons/13705dou2.gif)
其举例如下
值 字节1 字节2 字节3
0 00000000
1 00000001
2 00000010
127 01111111
128 10000000 00000001
129 10000001 00000001
130 10000010 00000001
16383 10000000 10000000 00000001
16384 10000001 10000000 00000001
16385 10000010 10000000 00000001
Chars 不定
![](/icons/13705dou.gif)
最少1字节 采用UTF-8编码[20]
![](/icons/13705de.gif)
Unicode
![](/icons/13705zifu.gif)
序列
String 不定
![](/icons/13705dou.gif)
最少2字节 由VInt和Chars组成
![](/icons/13705de.gif)
![](/icons/13705zifu.gif)
串类型
![](/icons/13705dou.gif)
VInt表示Chars
![](/icons/13705de.gif)
长度
![](/icons/13705dou.gif)
Chars则表示了String
![](/icons/13705de.gif)
值
以上
![](/icons/13705de.gif)
数据类型就是Lucene索引文件格式中用到
![](/icons/13705de.gif)
全部数据类型
![](/icons/13705dou.gif)
由于它们都以字节为基础定义而来
![](/icons/13705dou.gif)
因此保证了是平台无关
![](/icons/13705dou.gif)
这也是Lucene索引文件格式平台无关
![](/icons/13705de.gif)
主要原因
![](/icons/13705dou2.gif)
接下来我们看看Lucene索引文件
![](/icons/13705de.gif)
概念组成和结构组成
![](/icons/13705dou2.gif)
![](http://www.crazycoder.cn/WebFiles/20091/44845d64-d5b5-4fbe-bc36-cb87c4627124.g<img src='/icons/13705if.gif' />)
图 3.4 存储抽象实现UML图( 3)
图3.2到3.4展示了整个org.apache.lucene.store中主要
![](/icons/13705de.gif)
继承体系
![](/icons/13705dou2.gif)
共有 3个抽象类定义:Directory、InputStream和OutputStrem
![](/icons/13705dou.gif)
构成了
![](/icons/13705yi.gif)
个完整
![](/icons/13705de.gif)
基于抽象文件系统
![](/icons/13705de.gif)
存取体系结构
![](/icons/13705dou.gif)
在此基础上
![](/icons/13705dou.gif)
实作出了两个实现品:(FSDirectory
![](/icons/13705dou.gif)
FSInputStream
![](/icons/13705dou.gif)
FSOutputStream)和(RAMDirectory
![](/icons/13705dou.gif)
RAMInputStream和RAMOutputStream)
![](/icons/13705dou2.gif)
前者是以实际
![](/icons/13705de.gif)
文件系统做为基础实现
![](/icons/13705de.gif)
![](/icons/13705dou.gif)
后者则是建立在内存中
![](/icons/13705de.gif)
虚拟文件系统
![](/icons/13705dou2.gif)
前者主要用来永久
![](/icons/13705de.gif)
保存索引文件
![](/icons/13705dou.gif)
后者
![](/icons/13705de.gif)
作用则在于索引操作时是在内存中建立小
![](/icons/13705de.gif)
索引
![](/icons/13705dou.gif)
然后
![](/icons/13705yi.gif)
次性
![](/icons/13705de.gif)
输出合并到文件中去
![](/icons/13705dou.gif)
这
![](/icons/13705yi.gif)
点我们在后面
![](/icons/13705de.gif)
索引逻辑部分能够看到
![](/icons/13705dou2.gif)
此外
![](/icons/13705dou.gif)
还定以了org.apache.lucene.store.lock和org.apache.lucene.store.with两个辅助内部实现
![](/icons/13705de.gif)
类用在实现Directory思路方法
![](/icons/13705de.gif)
makeLock
![](/icons/13705de.gif)
时候
![](/icons/13705dou.gif)
以在锁定索引读写的前来让客户
![](/icons/13705chengxu.gif)
做
![](/icons/13705yi.gif)
些准备工作
![](/icons/13705dou2.gif)
(FSDirectory
![](/icons/13705dou.gif)
FSInputStream
![](/icons/13705dou.gif)
FSOutputStream)
![](/icons/13705de.gif)
内部实现依托于java语言中
![](/icons/13705de.gif)
io类库
![](/icons/13705dou.gif)
只是简单
![](/icons/13705de.gif)
做了
![](/icons/13705yi.gif)
个外部逻辑
![](/icons/13705de.gif)
包装
![](/icons/13705dou2.gif)
这当然要归功于java语言所提供
![](/icons/13705de.gif)
跨平台特性
![](/icons/13705dou.gif)
同时也带了
![](/icons/13705yi.gif)
些隐患:文件存取
![](/icons/13705de.gif)
效率提升需要依耐于文件类库
![](/icons/13705de.gif)
优化
![](/icons/13705dou2.gif)
如果需要继续优化文件存取
![](/icons/13705de.gif)
效率
![](/icons/13705dou.gif)
应该还提供
![](/icons/13705yi.gif)
个文件和目录
![](/icons/13705de.gif)
抽象
![](/icons/13705dou.gif)
以根据各种文件系统或者文件类型来提供
![](/icons/13705yi.gif)
个优化
![](/icons/13705de.gif)
机会
![](/icons/13705dou2.gif)
当然
![](/icons/13705dou.gif)
这是应用开发者所不需要关系
![](/icons/13705de.gif)
问题
![](/icons/13705dou2.gif)
(RAMDirectory
![](/icons/13705dou.gif)
RAMInputStream和RAMOutputStream)
![](/icons/13705de.gif)
内部实现就比较直接了
![](/icons/13705dou.gif)
直接采用了虚拟
![](/icons/13705de.gif)
文件RAMFile类(定义于文件RAMDirectory.java中)来表示文件
![](/icons/13705dou.gif)
目录则看作
![](/icons/13705yi.gif)
个String和RAMFile对应
![](/icons/13705de.gif)
关联
![](/icons/13705shuzu.gif)
![](/icons/13705dou2.gif)
RAMFile中采用
![](/icons/13705shuzu.gif)
来表示文件
![](/icons/13705de.gif)
存储空间
![](/icons/13705dou2.gif)
在此
![](/icons/13705de.gif)
基础上
![](/icons/13705dou.gif)
完成各项操作
![](/icons/13705de.gif)
实现
![](/icons/13705dou.gif)
就形成了基于内存
![](/icons/13705de.gif)
虚拟文件系统
![](/icons/13705dou2.gif)
![](/icons/13705yinwei.gif)
在实际使用时
![](/icons/13705dou.gif)
并不会牵涉到很大字节数量
![](/icons/13705de.gif)
文件
![](/icons/13705dou.gif)
因此这种设计是简单直接
![](/icons/13705de.gif)
![](/icons/13705dou.gif)
也是高效率
![](/icons/13705de.gif)
![](/icons/13705dou2.gif)
这部分
![](/icons/13705de.gif)
实现在理清楚继承体系后
![](/icons/13705dou.gif)
相当
![](/icons/13705de.gif)
简单
![](/icons/13705dou2.gif)
因此接下来
![](/icons/13705de.gif)
部分
![](/icons/13705dou.gif)
我们可以通过直接阅读源代码解决
![](/icons/13705dou2.gif)
接下来我们看看这个部分
![](/icons/13705de.gif)
源代码如何在实际中使用
![](/icons/13705de.gif)
![](/icons/13705yi.gif)
般来说
![](/icons/13705dou.gif)
我们使用
![](/icons/13705de.gif)
是抽象类提供
![](/icons/13705de.gif)
接口而不是实际
![](/icons/13705de.gif)
实现类本身
![](/icons/13705dou2.gif)
在实现类中
![](/icons/13705yi.gif)
般都含有几个静态
![](/icons/13705hanshu.gif)
![](/icons/13705dou.gif)
比如createFile
![](/icons/13705dou.gif)
它能够返回
![](/icons/13705yi.gif)
个OutputStream接口
![](/icons/13705dou.gif)
或者openFile
![](/icons/13705dou.gif)
它能够返回
![](/icons/13705yi.gif)
个InputStream接口
![](/icons/13705dou.gif)
利用这些接口的中
![](/icons/13705de.gif)
思路方法
![](/icons/13705dou.gif)
比如writeString
![](/icons/13705dou.gif)
writeByte等等
![](/icons/13705dou.gif)
我们就能够在抽象
![](/icons/13705de.gif)
层次上处理Lucene定义
![](/icons/13705de.gif)
数据类型
![](/icons/13705de.gif)
读写
![](/icons/13705dou2.gif)
简单
![](/icons/13705de.gif)
说
![](/icons/13705dou.gif)
Lucene中存储抽象这部分设计时采用了工厂模式(Factory parttern)[23]
![](/icons/13705dou2.gif)
我们利用静态类
![](/icons/13705de.gif)
思路方法也就是工厂来创建对象
![](/icons/13705dou.gif)
返回接口
![](/icons/13705dou.gif)
通过接口来执行操作
![](/icons/13705dou2.gif)
5、 有关cLucene项目
这
![](/icons/13705yi.gif)
部分详细
![](/icons/13705de.gif)
介绍说明了Lucene系统中所采用
![](/icons/13705de.gif)
索引文件格式、
![](/icons/13705yi.gif)
些基础类和存储抽象
![](/icons/13705dou2.gif)
接下来我们来叙述
![](/icons/13705yi.gif)
下我们在项目cLucene中重新实现这些结构时候
![](/icons/13705de.gif)
![](/icons/13705yi.gif)
些考虑
![](/icons/13705dou2.gif)
cLucene彻底
![](/icons/13705de.gif)
遵守了Lucene所定义
![](/icons/13705de.gif)
索引文件格式
![](/icons/13705dou.gif)
这是Lucene对于各个兼容系统
![](/icons/13705de.gif)
基本要求
![](/icons/13705dou2.gif)
在此基础上
![](/icons/13705dou.gif)
cLucene系统和Lucene系统才能够共享索引文件数据
![](/icons/13705dou2.gif)
或者说
![](/icons/13705dou.gif)
cLucene生成
![](/icons/13705de.gif)
索引文件和Lucene生成
![](/icons/13705de.gif)
索引文件完全等价
![](/icons/13705dou2.gif)
在基础类问题上
![](/icons/13705dou.gif)
cLucene同样封装了类似
![](/icons/13705de.gif)
结构
![](/icons/13705dou2.gif)
我们同样列表描述
![](/icons/13705dou.gif)
请和前面
![](/icons/13705de.gif)
表3.2和3.3对照比较
![](/icons/13705dou2.gif)
表 3.4 基础类包cLucene::util
类 介绍说明
Arrays 没有实现
![](/icons/13705dou.gif)
直接利用了STL库中
![](/icons/13705de.gif)
快排序算法实现
BitVector C/C
![](/icons/13705jiajia.gif)
语言版本
![](/icons/13705de.gif)
实现
![](/icons/13705dou.gif)
和java实现版本类似
Constants 常量静态类
![](/icons/13705dou.gif)
定义了
![](/icons/13705yi.gif)
些常量
![](/icons/13705dou.gif)
但是和java版本区别
![](/icons/13705de.gif)
是
![](/icons/13705dou.gif)
这里主要定义了
![](/icons/13705yi.gif)
些宏
PriorityQueue 这是
![](/icons/13705yi.gif)
个类型定义
![](/icons/13705dou.gif)
直接利用STL库中
![](/icons/13705de.gif)
std::priority_queue
表 3.3 基础类包cLucene::document
类 介绍说明
Document C/C
![](/icons/13705jiajia.gif)
语言版本
![](/icons/13705de.gif)
实现
![](/icons/13705dou.gif)
和java实现版本类似
Field C/C
![](/icons/13705jiajia.gif)
语言版本
![](/icons/13705de.gif)
实现
![](/icons/13705dou.gif)
和java实现版本类似
DateField 没有实现
![](/icons/13705dou.gif)
直接利用OpenTop库中
![](/icons/13705de.gif)
ot::StringUtil
存储抽象
![](/icons/13705de.gif)
实现上
![](/icons/13705dou.gif)
也同样是类似于java实现
![](/icons/13705dou2.gif)
由于我们采用了OpenTop库
![](/icons/13705dou.gif)
因此同样得以借助其中对于文件系统抽象
![](/icons/13705de.gif)
ot::io包来解决文件系统问题
![](/icons/13705dou2.gif)
这部分问题和前面
![](/icons/13705yi.gif)
样
![](/icons/13705dou.gif)
存在优化
![](/icons/13705de.gif)
可能
![](/icons/13705dou2.gif)
在实现
![](/icons/13705de.gif)
类层次上、对外接口上
![](/icons/13705dou.gif)
均和java版本
![](/icons/13705de.gif)
![](/icons/13705yi.gif)
样