由于分词工具用的用户字典有了更新,比如加入了一些出现频度较高的专有名词。
这时候希望通过重建索引,使查询结果更加准确。
但是,由于一些信息是当初建索引时加入的,而且这些信息是不能从原始文件中提取的,如当初的上传者是谁、上传日期 等。所以,不能够直接删除索引文件,重新来过。
为此,必须遍历原有索引,将其中进行了分析的Field重新分析并更新,不需要分析的Field则保持不变。
/**
* 为现有文件重新创建索引
* 例如当更新了用户字典时使用
*/
public void rebuildIndex(){
IndexReader ireader = null;
IndexWriter iwriter = null;
Directory directory = null;
try {
long start = new Date().getTime();
//前期准备工作
File indexPath = new File(SystemProperties.getIndexPath());
directory = FSDirectory.open(indexPath);
//实例化IKAnalyzer分词器
Analyzer analyzer = new IKAnalyzer();
//Analyzer analyzer = new CJKAnalyzer(Version.LUCENE_CURRENT);
//建立内存索引对象
ireader = IndexReader.open(directory);
if (indexPath.list().length > 0) {
// 已有以往索引
iwriter = new IndexWriter(directory, analyzer, false, IndexWriter.MaxFieldLength.LIMITED);
} else {
// 首次建立索引
iwriter = new IndexWriter(directory, analyzer, true, IndexWriter.MaxFieldLength.LIMITED);
}
//遍历每一已有Document
for (int i = 0; i < ireader.maxDoc(); i++) {
try {
// 提取原Document
Document oldDoc = ireader.document(i);
// 创建新Document
Document newDoc = new Document();
// 不变的Field直接从原Document中取
// KEY
newDoc.add(oldDoc.getField(Constants.FEILD_NAME_KEY));
// 文件名
newDoc.add(oldDoc.getField(Constants.FEILD_NAME_CLIENTNAME));
newDoc.add(oldDoc.getField(Constants.FEILD_NAME_SERVERNAME));
// 文件类型
newDoc.add(oldDoc.getField(Constants.FEILD_NAME_FILETYPE));
// 加入时间
newDoc.add(oldDoc.getField(Constants.FEILD_NAME_ADDTIME));
// 所属部门,用户查询时的权限控制
newDoc.add(oldDoc.getField(Constants.FEILD_NAME_OWNER));
// 不变的Field从原Document中取得后,重新Analyse
// 标题
String title = oldDoc.getField(Constants.FEILD_NAME_TITLE).stringValue();
newDoc.add(new Field(Constants.FEILD_NAME_TITLE, title, Field.Store.YES, Field.Index.ANALYZED));
// 内容
String text = oldDoc.getField(Constants.FEILD_NAME_CONTENTS).stringValue();
newDoc.add(new Field(Constants.FEILD_NAME_CONTENTS, text, Field.Store.YES, Field.Index.ANALYZED));
String key = oldDoc.getField(Constants.FEILD_NAME_KEY).stringValue();
// 用KEY做查询条件
Term term = new Term(Constants.FEILD_NAME_KEY, key);
// 替换原有的Document
iwriter.updateDocument(term, newDoc);
} catch (Throwable t) {
if (log.isErrorEnabled()) {
log.error(t.getMessage());
}
}
}
long end = new Date().getTime();
if (log.isDebugEnabled()) {
log.debug("Rebuild Index: " + ireader.maxDoc() + " documents, in " + (end - start) + " milliseconds.");
}
} catch (Throwable t) {
if (log.isErrorEnabled()) {
log.error(t.getMessage());
}
} finally {
if (ireader != null) {
try {
ireader.close();
} catch (AlreadyClosedException e) {
log.error(e.getMessage());
} catch (IOException e) {
log.error(e.getMessage());
}
}
if (iwriter != null) {
try {
// 注意这一句非常重要,否则虽然效果已经达到,但Documents数和存储空间都会翻倍!
// 但使用此方法的前提是,磁盘剩余空间必须有已用索引空间的2倍
// 此时由于重建,索引空间已经是翻倍的了,所以剩余空间应该有之前索引空间的4被!
iwriter.optimize();
iwriter.close();
} catch (AlreadyClosedException e) {
log.error(e.getMessage());
} catch (IOException e) {
log.error(e.getMessage());
}
}
if (directory != null) {
try {
directory.close();
} catch (IOException e) {
log.error(e.getMessage());
}
}
}
}
刚刚接触Lucene时间不长,不知道以上自己“杜撰”的代码是否可行,请大家多多指点。
- 大小: 3.2 KB
- 大小: 622 Bytes
分享到:
相关推荐
db-river-es 背景 ,深受欢迎的开源分布式搜索引擎,很多场景下,...定位:从数据库创建ElasticSearch全量索引,索引与数据库数据联动,实时更新 关键词:ElasticSearch index / mysql, sqlserver... / real time i
电信设备-融合哈希的频繁更新不确定移动对象索引方法.zip
代价分析是借助代价模型预测和评估空间索引结构的一种有效方法。针对索引的空间划分和数据划分这两种策略,在已有的索引结构基础上建立了向量空间划分类型索引的代价模型,该模型可实现查询以及动态更新的性能评价。...
当某张表建立时间比较长以及该表频繁的进行插入,更新操作时,将出现索引失效问题。
因为索引行是按索引键的顺序存储的,所以当索引键中有一列被更新时,DBMS可能不得不把相应的行从旧的索引位置移到新的位置来保持这一顺序,所以不稳定的列不建议被索引。在实际开发中,这个问题不可能避免(比如按...
(4)使用“实验一”中的数据库“abc”,练习使用触发器,在销售表上创建触发器tr_updateprice,每次新增销售记录时,自动更新产品表的单价,更新方法是:每增加一笔销售记录,就将该产品的单价减去1块钱。...
电信设备-一种全文检索系统中索引信息的更新方法以及装置.zip
然后采用B 树方法对路径索引的存储、更新和查找方法进行了设计实现;最后采用图数据库Neo4j对路径索引存储空间和查询性能进行了测试。结果表明,虽然路径索引会占用存储空间,但是能够提高特定的查询处理的性能。
一個可擴展的框架,將支持強大的空間索引方法。 支持複雜的空間查詢。範圍、點位置、最近鄰和 k 最近鄰以及參數查詢(由空間約束定義)應該易於部署和運行。 易於使用的界面,用於插入、刪除和更新信息。 多種定制...
首先,我的索引结构是酱紫的。 ...以上所述是小编给大家介绍的Python中elasticsearch插入和更新数据的实现方法,希望对大家有所帮助,如果大家有任何疑问欢迎给我留言,小编会及时回复大家的!
1. 熟练掌握使用企业管理器和T-SQL语句创建、查询、更新、修改和删除视图。 2. 进一步掌握视图与基本表的联系与区别。 3. 理解索引的概念和作用。 4. 熟练掌握索引的创建与删除
更新表中索引列上的数据时,索引会被自动更新,确保索引树与表中的内容完全保持一致,因此索引越多,则更新时长更长。 根据用途,索引在逻辑上大体分为三类 普通索引(INDEX): 最基本的索引类型,没有任何限制。...
提出了一种基于倒排表的索引,能很好地支持文档结构和内容的动态更新。该索引结构建有基于词条的水平索引和基于元素标志GID的垂直...另外给出了基于上下文共现分析技术的语义检索和利用关系数据库实现该索引的方法。
数据库索引是一个数据结构,提高操作的速度,在一个表中可以...究其原因是,当进行插入或更新,数据库以及需要惰性或更新索引值。 简单的唯一索引: 可以创建一个唯一索引的表。唯一的索引意味着两个行不能拥有相同的索
一般的应用系统,读写比例在10:1左右,而且插入操作和一般的更新操作很少出现性能问题,在生产环境中,我们遇到最多的,也是最容易出问题的,还是一些复杂的查询操作,因此对查询语句的优化显然是重中之重。...
因为太多的索引与不充分、不正确的索引对性能都毫无益处:在表上建立的每个索引都会增加存储开销,索引对于插入、删除、更新操作也会增加处理上的开销。 另外,过多的复合索引,在有单字段索引的情况下,一般都是...
Oracle10g中context类型的全文索引也可以自动同步了。10g中新引入了2种同步的方式,现在有3种 1、ctx_ddl.sync_index2、sync(on commit)3、sync( every …) in parameter setting while creating index sync(on ...
在对比分析位图索引结构中的简单位图索引和编码位图索引的基础上,提出了一种新的基于双向有序链表存储的动态编码位图索引方法,并给出了这一动态编码位图索引方法在数据插入、删除、更新和检索中的详细算法。...
一.索引的基础概念 1.数据库索引是什么? 数据库索引是数据库管理系统(DBMS)中一个排序的数据结构,以协助快速查询和更新数据库中表的结构. 2.索引的类型 普通索引:是最基本的索引,它没有任何限制, ...3.索引方法:
在了解覆盖索引之前我们先大概了解一下什么是聚集索引(主键索引)和辅助索引(二级索引) 聚集索引(主键索引): 聚集索引就是按照每张表的主键构造一颗B+树,同时叶子节点中...解释二: 索引是高效找到行的一个方法,