Lucene 3.0.0 的TokenStream与Analyzer

Lucene 3.0.0 的TokenStream与Analyzer如果你看的Lucene相关的书是很老版本的,比如说2.4或者更早,那么对于这个版本中的Analyzer可能就不那么容易接受了,我也是看的<lucene分析与应用>这本书,比较古老的版本.今天读了一下源代码,大概说说心得,我从SimpleAnalyzer说起.SimpleAnalyzer的作用就是把一段字符串中除了符号和非文字的内容作为分…

大家好,又见面了,我是你们的朋友全栈君。

     如果你看的Lucene相关的书是很老版本的, 比如说2.4或者更早, 那么对于这个版本中的Analyzer可能就不那么容易接受了, 我也是看的<lucene分析与应用>这本书, 比较古老的版本.

     今天读了一下源代码, 大概说说心得, 我从SimpleAnalyzer说起.

     SimpleAnalyzer的作用就是把一段字符串中除了符号和非文字的内容作为分隔, 把句子分成很多的单词. 对于中文也可以用来剔除标点符号

public TokenStream tokenStream(String fieldName, Reader reader) {
    
    
  return new LowerCaseTokenizer(reader);
}

     SimpleAnalyzer的TokenStream就是调用了LowerCaseTokenizer的构造函数. LowerCaseTokenizer继承自CharTokenizer. 首先来看看CharTokenizer的构造函数吧:

public CharTokenizer(Reader input) {
    
    
  super(input);
  offsetAtt = addAttribute(OffsetAttribute.class);
  termAtt = addAttribute(TermAttribute.class);
}

     除了调用基类的构造函数外(继承自Tokenizer), 另外还有下面两个与Attribute相关的语句, Attribute是Lucene新增的内容(具体是不是3.0新增的就不清楚了), 作用是可以在TokenStream中加入一些用户需要的内容, 比如说单词的词性, 文字等等内容, 这些东西是可以用户定义的, 提供了更多的耦合性, 怎么访问这些内容我上一篇日志也是有说的.

     下面我把CharTokenizer的incrementToken()函数的代码贴出来分析一下

public final boolean incrementToken() throws IOException {
    
    
  clearAttributes();
  int length = 0;
  int start = bufferIndex;
  char[] buffer = termAtt.termBuffer();
  while (true) {
    
    
 
    if (bufferIndex >= dataLen) {
    
    
      offset += dataLen;
      dataLen = input.read(ioBuffer);
      if (dataLen == -1) {
    
    
        dataLen = 0;                            // so next offset += dataLen won't decrement offset
        if (length > 0)
          break;
        else
          return false;
      }
      bufferIndex = 0;
    }
 
    final char c = ioBuffer[bufferIndex++];
 
    if (isTokenChar(c)) {               // if it's a token char
 
      if (length == 0)                 // start of token
        start = offset + bufferIndex - 1;
      else if (length == buffer.length)
        buffer = termAtt.resizeTermBuffer(1+length);
 
      buffer[length++] = normalize(c); // buffer it, normalized
 
      if (length == MAX_WORD_LEN)      // buffer overflow!
        break;
 
    } else if (length > 0)             // at non-Letter w/ chars
      break;                           // return 'em
  }
 
  termAtt.setTermLength(length);
  offsetAtt.setOffset(correctOffset(start), correctOffset(start+length));
  return true;
}

     在一个Tokenizer里面将保留这多个Attribute的实例, 这些实例是循环利用的, 每新得到一个单词, 就改写一下他们的内容,

1)

if (bufferIndex >= dataLen) {
    
    
  offset += dataLen;
  dataLen = input.read(ioBuffer);
  if (dataLen == -1) {
    
    
    dataLen = 0;                            // so next offset += dataLen won't decrement offset
    if (length > 0)
      break;
    else
      return false;
  }
  bufferIndex = 0;
}

这段代码是初始化的内容, 得到整个字符串的长度, ioBuffer就是这个字符串

2)

final char c = ioBuffer[bufferIndex++];
 
if (isTokenChar(c)) {               // if it's a token char
 
  if (length == 0)                 // start of token
    start = offset + bufferIndex - 1;
  else if (length == buffer.length)
    buffer = termAtt.resizeTermBuffer(1+length);
 
  buffer[length++] = normalize(c); // buffer it, normalized
 
  if (length == MAX_WORD_LEN)      // buffer overflow!
    break;
 
} else if (length > 0)             // at non-Letter w/ chars
  break;                           // return 'em

这段代码是不停的读取下一个字符, 看看是符号还是合法的字符.

3)

termAtt.setTermLength(length);
offsetAtt.setOffset(correctOffset(start), correctOffset(start+length));
return true;

最后把单词的termAtt和offsetAtt赋值, 返回

转载于:https://www.cnblogs.com/LeftNotEasy/archive/2010/01/17/1650139.html

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/163122.html原文链接:https://javaforall.net

(0)
全栈程序员-站长的头像全栈程序员-站长


相关推荐

  • 一维卷积神经网络案例_matlab 卷积神经网络

    一维卷积神经网络案例_matlab 卷积神经网络基于一维卷积神经网络对机械振动信号进行分类并加以预测*使用一维卷积神经网络训练振动信号进行二分类2020年7月16日,一学期没等到开学,然而又放假了。总览CSDN中大多数卷积神经网络都是对二维图片进行分类的,而图片也都是常见的猫狗分类,minst手写数字分类。一维卷积神经网络的使用非常少见,有也是IDMB情感分类,和鸢尾花分类的。作者研究生就读于河北一所双飞,全国排名270多,哈哈哈,不吹不黑。在网上翻来翻去找不到一篇可以利用的代码去研究我的机械故障诊断,后来在无奈下到某宝搜寻到一段代码,可以利用

    2022年9月22日
    3
  • php function 定义时函数名前加&符号的意义[通俗易懂]

    php function 定义时函数名前加&符号的意义

    2022年2月9日
    36
  • 助臂_有所臂助

    助臂_有所臂助第十章助臂  一个好汉三个帮,程序员同样如此。  我怀着异样的心情去了天龙。也许是ANGEL的出现感染了我,给我感觉到了压迫,我比往常更努力的投入到工作中去,我必须尽快完成眼前这个工程,然后全心投入到智能杀毒软件的研究中去。  思考再三后,我还是把DENNIS信里的内容告诉了李珏和赵思聪,他两当场就被震住了。  “真的可能写出智能化的病毒吗?”赵思聪不可思议的问道。  我点了点头,无奈的说道:

    2022年8月31日
    6
  • unit在matlab中啥意思,unit8(matlab中uint8函数)

    unit在matlab中啥意思,unit8(matlab中uint8函数)就是宏定义,代码中就用这些去定义变量如uint16a;就表示定义了一个无符号整形变量a(等价于unsignedinta;)其他的同理其作用是程序更加简洁最大的作用是增.将变量t类型强制转换为uint8*类型也就是转换成指向uint8类型变量的指针变量uint8应该是无符号8位二进制整型,其实就是unsignedchar类型。一定要是新教材!!!美国的复感恩节。在大多…

    2022年9月17日
    3
  • dropdown list_css中display中flex

    dropdown list_css中display中flexサンプル画面–>http://ns.adobe.com/mxml/2009″    xmlns:s=”library://ns.adobe.com/flex/spark”    xmlns:mx=”library://ns.adobe.com/flex/mx”    minWidth=”800″    minHeight=”400″>      import

    2022年10月10日
    3
  • 在C#中ParameterizedThreadStart和ThreadStart区别

    在C#中ParameterizedThreadStart和ThreadStart区别
    不需要传递参数,也不需要返回参数
      我们知道启动一个线程最直观的办法是使用Thread类,具体步骤如下:
    ThreadStartthreadStart=newThreadStart(Calculate);Threadthread=newThread(threadStart);thread.Start();publicvoidCalculate(){ doubleDiameter=0.5; Console.Write(“T

    2022年7月15日
    12

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号