教你如何修改源代码使paoding庖丁分词器支持最新版本Lucene3.0.2
2010-07-09 14:48
465 查看
大家都喜欢开源,不过其有一个问题就是版本的兼容性问题。
去年我还在用lucene2.3现在却到了3.0.2.而qieqie前辈估计很忙,所以对于兼容Lucene3的版本的paoding迟迟未发布。
在google代码网http://code.google.com/p/paoding/issues/detail?id=49#makechanges有提供的三个文件用来覆盖原有的代码使paoding兼容Lucene3.
而我们是直接采用svn同步了paoding的最新代码,嵌入到我们的项目。同事在lucene3.0.1上没有听说有报错问题,但是我把它嵌入到lucene3.0.2版本下却报:
Exception in thread "main" java.lang.NullPointerException
at net.paoding.analysis.analyzer.PaodingTokenizer.close(PaodingTokenizer.java:164)
at org.apache.lucene.queryParser.QueryParser.getFieldQuery(QueryParser.java:571)
at org.apache.lucene.queryParser.QueryParser.Term(QueryParser.java:1362)
at org.apache.lucene.queryParser.QueryParser.Clause(QueryParser.java:1250)
at org.apache.lucene.queryParser.QueryParser.Query(QueryParser.java:1178)
at org.apache.lucene.queryParser.QueryParser.TopLevelQuery(QueryParser.java:1167)
at org.apache.lucene.queryParser.QueryParser.parse(QueryParser.java:182)
at test.TestBoBo.main(TestBoBo.java:44)
最后看到关于paoding支持solr1.4的文章:
转:http://www.odoc.info/?p=185
由于solr1.4使用Lucene 2.9.1 ,故需要修改庖丁源代码:net.paoding.analysis.analyzer.PaodingTokenizer
需要注意的有两点
1. 继承关系由 TokenStream 调整为 Tokenizer,因此需要删除变量
private final Reader input;
删除对应的关闭方法
public void close() throws IOException {
super.close();
input.close();
}
2. 高亮显示功能由于底层实现变化,故需要重写reset方法。原先reset 只是调整input。现在需要将多个值重置。
public void reset(Reader input) throws IOException {
this.input = input;
this.inputLength=0;
this.offset=0;
this.dissected=0;
this.tokenIteractor=null;
this.beef.set(0, 0);
}
调整后的代码如下:
public final class PaodingTokenizer extends Tokenizer implements Collector {
// -------------------------------------------------
/**
* 从input读入的总字符数
*/
private int inputLength;
/**
*
*/
private static final int bufferLength = 128;
/**
* 接收来自{@link #input}的文本字符
*
* @see #next()
*/
private final char[] buffer = new char[bufferLength];
/**
* {@link buffer}[0]在{@link #input}中的偏移
*
* @see #collect(String, int, int)
* @see #next()
*/
private int offset;
/**
*
*/
private final Beef beef = new Beef(buffer, 0, 0);
/**
*
*/
private int dissected;
/**
* 用于分解beef中的文本字符,由PaodingAnalyzer提供
*
* @see #next()
*/
private Knife knife;
/**
*
*/
private TokenCollector tokenCollector;
/**
* tokens迭代器,用于next()方法顺序读取tokens中的Token对象
*
* @see #tokens
* @see #next()
*/
private Iterator<Token> tokenIteractor;
private TermAttribute termAtt;
private OffsetAttribute offsetAtt;
private TypeAttribute typeAtt;
// -------------------------------------------------
/**
*
* @param input
* @param knife
* @param tokenCollector
*/
public PaodingTokenizer(Reader input, Knife knife,
TokenCollector tokenCollector) {
this.input = input;
this.knife = knife;
this.tokenCollector = tokenCollector;
init();
}
private void init() {
termAtt = addAttribute(TermAttribute.class);
offsetAtt = addAttribute(OffsetAttribute.class);
typeAtt = addAttribute(TypeAttribute.class);
}
// -------------------------------------------------
public TokenCollector getTokenCollector() {
return tokenCollector;
}
public void setTokenCollector(TokenCollector tokenCollector) {
this.tokenCollector = tokenCollector;
}
// -------------------------------------------------
public void collect(String word, int offset, int end) {
tokenCollector.collect(word, this.offset + offset, this.offset + end);
}
// -------------------------------------------------
public int getInputLength() {
return inputLength;
}
// -------------------------------------------------
//update by stt 2010-07-09
//reason:报空指针错误
/*@Override
public void close() throws IOException {
super.close();
input.close();
}*/
@Override
public boolean incrementToken() throws IOException {
// 已经穷尽tokensIteractor的Token对象,则继续请求reader流入数据
while (tokenIteractor == null || !tokenIteractor.hasNext()) {
// System.out.println(dissected);
int read = 0;
int remainning = -1;// 重新从reader读入字符前,buffer中还剩下的字符数,负数表示当前暂不需要从reader中读入字符
if (dissected >= beef.length()) {
remainning = 0;
} else if (dissected < 0) {
remainning = bufferLength + dissected;
}
if (remainning >= 0) {
if (remainning > 0) {
System.arraycopy(buffer, -dissected, buffer, 0, remainning);
}
read = input
.read(buffer, remainning, bufferLength - remainning);
inputLength += read;
int charCount = remainning + read;
if (charCount < 0) {
// reader已尽,按接口next()要求返回null.
return false;
}
if (charCount < bufferLength) {
buffer[charCount++] = 0;
}
// 构造“牛”,并使用knife“解”之
beef.set(0, charCount);
offset += Math.abs(dissected);
// offset -= remainning;
dissected = 0;
}
dissected = knife.dissect((Collector) this, beef, dissected);
// offset += read;// !!!
tokenIteractor = tokenCollector.iterator();
}
// 返回tokensIteractor下一个Token对象
Token token = tokenIteractor.next();
termAtt.setTermBuffer(token.term());
offsetAtt.setOffset(correctOffset(token.startOffset()),
correctOffset(token.endOffset()));
typeAtt.setType("paoding");
return true;
}
@Override
public void reset(Reader input) throws IOException {
//update by stt 2010-07-09
//reason:报空指针错误
/*super.reset();
offset = 0;
inputLength = 0;*/
this.input = input;
this.inputLength=0;
this.offset=0;
this.dissected=0;
this.tokenIteractor=null;
this.beef.set(0, 0);
}
}
运行后没有再报此错。
去年我还在用lucene2.3现在却到了3.0.2.而qieqie前辈估计很忙,所以对于兼容Lucene3的版本的paoding迟迟未发布。
在google代码网http://code.google.com/p/paoding/issues/detail?id=49#makechanges有提供的三个文件用来覆盖原有的代码使paoding兼容Lucene3.
而我们是直接采用svn同步了paoding的最新代码,嵌入到我们的项目。同事在lucene3.0.1上没有听说有报错问题,但是我把它嵌入到lucene3.0.2版本下却报:
Exception in thread "main" java.lang.NullPointerException
at net.paoding.analysis.analyzer.PaodingTokenizer.close(PaodingTokenizer.java:164)
at org.apache.lucene.queryParser.QueryParser.getFieldQuery(QueryParser.java:571)
at org.apache.lucene.queryParser.QueryParser.Term(QueryParser.java:1362)
at org.apache.lucene.queryParser.QueryParser.Clause(QueryParser.java:1250)
at org.apache.lucene.queryParser.QueryParser.Query(QueryParser.java:1178)
at org.apache.lucene.queryParser.QueryParser.TopLevelQuery(QueryParser.java:1167)
at org.apache.lucene.queryParser.QueryParser.parse(QueryParser.java:182)
at test.TestBoBo.main(TestBoBo.java:44)
最后看到关于paoding支持solr1.4的文章:
转:http://www.odoc.info/?p=185
由于solr1.4使用Lucene 2.9.1 ,故需要修改庖丁源代码:net.paoding.analysis.analyzer.PaodingTokenizer
需要注意的有两点
1. 继承关系由 TokenStream 调整为 Tokenizer,因此需要删除变量
private final Reader input;
删除对应的关闭方法
public void close() throws IOException {
super.close();
input.close();
}
2. 高亮显示功能由于底层实现变化,故需要重写reset方法。原先reset 只是调整input。现在需要将多个值重置。
public void reset(Reader input) throws IOException {
this.input = input;
this.inputLength=0;
this.offset=0;
this.dissected=0;
this.tokenIteractor=null;
this.beef.set(0, 0);
}
调整后的代码如下:
public final class PaodingTokenizer extends Tokenizer implements Collector {
// -------------------------------------------------
/**
* 从input读入的总字符数
*/
private int inputLength;
/**
*
*/
private static final int bufferLength = 128;
/**
* 接收来自{@link #input}的文本字符
*
* @see #next()
*/
private final char[] buffer = new char[bufferLength];
/**
* {@link buffer}[0]在{@link #input}中的偏移
*
* @see #collect(String, int, int)
* @see #next()
*/
private int offset;
/**
*
*/
private final Beef beef = new Beef(buffer, 0, 0);
/**
*
*/
private int dissected;
/**
* 用于分解beef中的文本字符,由PaodingAnalyzer提供
*
* @see #next()
*/
private Knife knife;
/**
*
*/
private TokenCollector tokenCollector;
/**
* tokens迭代器,用于next()方法顺序读取tokens中的Token对象
*
* @see #tokens
* @see #next()
*/
private Iterator<Token> tokenIteractor;
private TermAttribute termAtt;
private OffsetAttribute offsetAtt;
private TypeAttribute typeAtt;
// -------------------------------------------------
/**
*
* @param input
* @param knife
* @param tokenCollector
*/
public PaodingTokenizer(Reader input, Knife knife,
TokenCollector tokenCollector) {
this.input = input;
this.knife = knife;
this.tokenCollector = tokenCollector;
init();
}
private void init() {
termAtt = addAttribute(TermAttribute.class);
offsetAtt = addAttribute(OffsetAttribute.class);
typeAtt = addAttribute(TypeAttribute.class);
}
// -------------------------------------------------
public TokenCollector getTokenCollector() {
return tokenCollector;
}
public void setTokenCollector(TokenCollector tokenCollector) {
this.tokenCollector = tokenCollector;
}
// -------------------------------------------------
public void collect(String word, int offset, int end) {
tokenCollector.collect(word, this.offset + offset, this.offset + end);
}
// -------------------------------------------------
public int getInputLength() {
return inputLength;
}
// -------------------------------------------------
//update by stt 2010-07-09
//reason:报空指针错误
/*@Override
public void close() throws IOException {
super.close();
input.close();
}*/
@Override
public boolean incrementToken() throws IOException {
// 已经穷尽tokensIteractor的Token对象,则继续请求reader流入数据
while (tokenIteractor == null || !tokenIteractor.hasNext()) {
// System.out.println(dissected);
int read = 0;
int remainning = -1;// 重新从reader读入字符前,buffer中还剩下的字符数,负数表示当前暂不需要从reader中读入字符
if (dissected >= beef.length()) {
remainning = 0;
} else if (dissected < 0) {
remainning = bufferLength + dissected;
}
if (remainning >= 0) {
if (remainning > 0) {
System.arraycopy(buffer, -dissected, buffer, 0, remainning);
}
read = input
.read(buffer, remainning, bufferLength - remainning);
inputLength += read;
int charCount = remainning + read;
if (charCount < 0) {
// reader已尽,按接口next()要求返回null.
return false;
}
if (charCount < bufferLength) {
buffer[charCount++] = 0;
}
// 构造“牛”,并使用knife“解”之
beef.set(0, charCount);
offset += Math.abs(dissected);
// offset -= remainning;
dissected = 0;
}
dissected = knife.dissect((Collector) this, beef, dissected);
// offset += read;// !!!
tokenIteractor = tokenCollector.iterator();
}
// 返回tokensIteractor下一个Token对象
Token token = tokenIteractor.next();
termAtt.setTermBuffer(token.term());
offsetAtt.setOffset(correctOffset(token.startOffset()),
correctOffset(token.endOffset()));
typeAtt.setType("paoding");
return true;
}
@Override
public void reset(Reader input) throws IOException {
//update by stt 2010-07-09
//reason:报空指针错误
/*super.reset();
offset = 0;
inputLength = 0;*/
this.input = input;
this.inputLength=0;
this.offset=0;
this.dissected=0;
this.tokenIteractor=null;
this.beef.set(0, 0);
}
}
运行后没有再报此错。
相关文章推荐
- 最新Wordpress 3.5版本如何修改图片默认上传目录路径
- Wordpress最新3.5版本如何修改图片默认上传目录路径
- Wordpress最新3.5版本如何修改图片默认上传目录路径
- [置顶] Github如何提交修改的代码以及更新到最新版本
- QQ2009聊天文本记录器 完成发布,支持目前最新的QQ2009 SP1版本。
- 如何修改两个PHP版本,php-v和phpinfo两个不同的版本
- 由源代码编译SpriteBuilder最新版本1.5.0搭配最新的Cocos2D 3.4.9
- android最新源代码的编译及运行(android版本5.0.1r,编译系统ubuntu14.10 x64)
- Lucene.Net 2.3.1开发介绍——附录一、如何下载Lucene.Net的各种版本
- 如何添加Lucene的源代码及注释!
- 如何配置修改并调试opencv源代码
- 最新火狐手机浏览器如何通过firefox修改UA
- 如何修改maven的默认jdk版本
- Android如何使用最新版本百度地图地图 SDK v4.2.1(一)的API
- 修改phpcmsv9网站系统最新版本tag的伪静态设置
- Lucene全文搜索之分词器:使用IK Analyzer中文分词器(修改IK Analyzer源码使其支持lucene5.5.x)
- 该如何解决Tomcat支持的J2EE版本的冲突问题
- 最新历史版本 :Android修改system只读权限:remount
- C#生成的应用程序版本如何修改
- 如何升级centos到最新版本