`
twh1224
  • 浏览: 96017 次
  • 性别: Icon_minigender_1
  • 来自: 武汉
社区版块
存档分类
最新评论

Lucene学习(8)

阅读更多
Lucene分析器的实现。
Lucene(分词)过滤器TokenFilter类,以及继承它的子类的实现类。
TokenFilter是一个抽象类,定义了对一个经过分词(Tokenizer)后的TokenStream进行过滤的功能,它的源代码如下所示:

 
package org.apache.lucene.analysis; 
 
import java.io.IOException; 
 
public abstract class TokenFilter extends TokenStream { 
// 通过输入一个TokenStream 
protected TokenStream input; 
 
protected TokenFilter(TokenStream input) { 
    this.input = input; 
} 
 
public void close() throws IOException { 
    input.close(); 
} 
} 


ChineseFilter中文过滤器类:

package org.apache.lucene.analysis.cn;

import java.util.Hashtable;
import org.apache.lucene.analysis.*;

// 中文过滤器,包含了含有外文字符的情况,因为中文搜索的关键字可能是:中文+外文 

public final class ChineseFilter extends TokenFilter {

	// 这里给出了英文的终止词汇,如果直接调用根本对中文没有过滤作用,或者也可以在此添加终止词汇,比如:“也、了、啊、吧、呵……”等等一些助词叹词,因为这些词语对于检索没有意义 
	public static final String[] STOP_WORDS = { "and", "are", "as", "at", "be",
			"but", "by", "for", "if", "in", "into", "is", "it", "no", "not",
			"of", "on", "or", "such", "that", "the", "their", "then", "there",
			"these", "they", "this", "to", "was", "will", "with" };

	private Hashtable stopTable;

	// 构造函数,初始化一个终止词汇表 (过滤掉的词汇)   

	public ChineseFilter(TokenStream in) {
		super(in);

		stopTable = new Hashtable(STOP_WORDS.length);
		for (int i = 0; i < STOP_WORDS.length; i++)
			stopTable.put(STOP_WORDS[i], STOP_WORDS[i]);
	}

	// 如果stopTable为空,说明该过滤类根本没有进行过滤,直接将读入的词条(Token)返回 

	public final Token next() throws java.io.IOException {

		for (Token token = input.next(); token != null; token = input.next()) {
			String text = token.termText(); // 获取分词后词条的内容 

			// 这里,如果chineseChar是单个字,则Character.getType(chineseChar)返回的类型值为5;大写英文字符类型值为1,小写字符类型值为2 
			if (stopTable.get(text) == null) { // 如果分词后的词条内容没有出现在过滤列表stopTable中 
				switch (Character.getType(text.charAt(0))) {

				case Character.LOWERCASE_LETTER:
				case Character.UPPERCASE_LETTER:

					// 如果英文词条不是单个字符 
					if (text.length() > 1) {
						return token;
					}
					break;
				case Character.OTHER_LETTER:

					// 如果中文的过滤词汇表中是单个字的形式,则若是一个词汇中有一个字出现在stopTable中,那么整个词条都被过滤掉了。这是不合理的;所以只要把stopTable设置为空就可以实现,即不对分词的词条进行过滤 
					// 也可以在这里添加对词条的限制,来实现过滤 

					return token;
				}

			}

		}
		return null;
	}

}


再看一个限制词条长度的过滤器类:

package org.apache.lucene.analysis;

import java.io.IOException;

// 词条过长或者过短,则过滤掉 
public final class LengthFilter extends TokenFilter {

	final int min;
	final int max;

	// 构造函数,初始化此条长度上限和下限 
	public LengthFilter(TokenStream in, int min, int max) {
		super(in);
		this.min = min;
		this.max = max;
	}

	// 返回长度在min与max之间的词条 
	public final Token next() throws IOException {
		for (Token token = input.next(); token != null; token = input.next()) {
			int len = token.termText().length();
			if (len >= min && len <= max) {
				return token;
			}
			// note: else we ignore it but should we index each part of it? 
		}

		return null;
	}
}


可见,过滤器的目的就是对分词获得的词条的一些属性信息进行过滤,原则是:这些属性信息对检索没有实际意义。通过阅读标准过滤器类,再综合各种需要,我们就能根据自己的需要实现词条的过滤。Lucene包里给出的标准过滤器类。其实是对英文字符过滤的的,源代码如下:

package org.apache.lucene.analysis.standard;

import org.apache.lucene.analysis.*;

public final class StandardFilter extends TokenFilter implements
		StandardTokenizerConstants {

	public StandardFilter(TokenStream in) {
		super(in);
	}

	// APOSTROPHE、ACRONYM等都是在一个常量接口类StandardTokenizerConstants里定义的常量,分别代表在过滤中可能要对其进行处理的字符 

	private static final String APOSTROPHE_TYPE = tokenImage[APOSTROPHE];
	private static final String ACRONYM_TYPE = tokenImage[ACRONYM];

	// 如果词条不空,进行处理后返回经过过滤处理后的词条 
	public final org.apache.lucene.analysis.Token next()
			throws java.io.IOException {
		org.apache.lucene.analysis.Token t = input.next();

		if (t == null)
			return null;

		String text = t.termText();
		String type = t.type();

		// 英文中的 's或'S对检索意义不大,可以删除掉 
		if (type == APOSTROPHE_TYPE
				&& (text.endsWith("'s") || text.endsWith("'S"))) {
			return new org.apache.lucene.analysis.Token(text.substring(0, text
					.length() - 2), t.startOffset(), t.endOffset(), type);

		} else if (type == ACRONYM_TYPE) { // 对“圆点”进行处理,直接把出现的“圆点”删除掉,保留其它字符 
			StringBuffer trimmed = new StringBuffer();
			for (int i = 0; i < text.length(); i++) {
				char c = text.charAt(i);
				if (c != '.')
					trimmed.append(c);
			}
			return new org.apache.lucene.analysis.Token(trimmed.toString(), t
					.startOffset(), t.endOffset(), type);

		} else {
			return t;
		}
	}
}


常量接口类StandardTokenizerConstants 定义如下:

package org.apache.lucene.analysis.standard; 
 
public interface StandardTokenizerConstants { 
 
int EOF = 0; 
int ALPHANUM = 1; 
int APOSTROPHE = 2; 
int ACRONYM = 3; 
int COMPANY = 4; 
int EMAIL = 5; 
int HOST = 6; 
int NUM = 7; 
int P = 8; 
int HAS_DIGIT = 9; 
int ALPHA = 10; 
int LETTER = 11; 
int CJ = 12; 
int KOREAN = 13; 
int DIGIT = 14; 
int NOISE = 15; 
 
int DEFAULT = 0; 
 
String[] tokenImage = { 
    "<EOF>", 
    "<ALPHANUM>", 
    "<APOSTROPHE>", 
    "<ACRONYM>", 
    "<COMPANY>", 
    "<EMAIL>", 
    "<HOST>", 
    "<NUM>", 
    "<P>", 
    "<HAS_DIGIT>", 
    "<ALPHA>", 
    "<LETTER>", 
    "<CJ>", 
    "<KOREAN>", 
    "<DIGIT>", 
    "<NOISE>", 
}; 
} 


还有一个org.apache.lucene.analysis.StopFilter类,和ChineseFilter类的实现很相似,只是这里把过滤字符列表是初始化一个StopFilter过滤器的时候指定的,而且该类实现了对过滤字符类表中字符进行转换的功能。

我感觉,最应该好好研究的是关于同义词的过滤问题。Lucene包中给了一个 org.apache.lucene.index.memory.SynonymTokenFilter过滤类,比较复杂,因为这里面涉及到了一个重要的类:org.apache.lucene.index.memory.SynonymMap。通过研究对英文中同义词的过滤,来考虑中文同义词过滤的问题。
分享到:
评论

相关推荐

    lucene学习资料收集

    【标题】:“Lucene学习资料收集” 【描述】:Lucene是一个开源的全文搜索引擎库,由Apache软件基金会开发。这个资料集可能包含了关于如何理解和使用Lucene的各种资源,特别是通过博主huanglz19871030在iteye上的...

    Lucene的的学习资料及案例

    **Lucene学习指南** Lucene是一个高性能、全文检索库,由Apache软件基金会开发并维护,是Java编程语言中广泛使用的搜索引擎库。它提供了一个简单的API,使得开发者能够方便地在应用中实现全文检索功能。本篇文章将...

    lucene学习pdf2

    "lucene学习pdf2" 提供的文档,无疑是对Lucene深入理解的一把钥匙,它涵盖了Lucene的核心概念、操作流程以及高级特性。 首先,Lucene的基础知识是必不可少的。Lucene的核心在于索引和搜索,它将非结构化的文本数据...

    lucene学习

    Lucene的基础知识 1、案例分析:什么是全文检索,如何实现全文检索 2、Lucene实现全文检索的流程 a) 创建索引 b) 查询索引 3、配置开发环境 4、创建索引库 5、查询索引库 6、分析器的分析过程 a) 测试分析器的分词...

    Lucene学习源码.rar

    本文将主要围绕Java Lucene进行深入探讨,并基于提供的“Lucene学习源码.rar”文件中的“Lucene视频教程_讲解部分源码”展开讨论。 一、Lucene核心概念 1. 文档(Document):Lucene中的基本单位,用于存储待检索...

    lucene学习资料

    《Lucene学习资料》 Lucene是一个开源的全文搜索引擎库,由Apache软件基金会维护。它提供了高级的文本分析和索引功能,使得开发者能够轻松地在应用程序中集成强大的搜索功能。这个资料包中的《Lucene in Action_2nd...

    Lucene-2.0学习文档

    本篇文章将围绕"Lucene-2.0学习文档"的主题,结合Indexer.java、MyScoreDocComparator.java和MySortComparatorSource.java这三个关键文件,深入探讨Lucene的核心概念和实际应用。 首先,我们来看`Indexer.java`。这...

    Lucene3.3.0学习Demo

    **Lucene 3.3.0 学习Demo** Lucene是一个开源的全文搜索引擎库,由Apache软件基金会开发。在3.3.0版本中,Lucene提供了强大的文本搜索功能,包括分词、索引创建、查询解析和结果排序等。这个"Lucene3.3.0学习Demo...

    lucene学习-02

    【标题】:“Lucene学习-02” 在深入探讨“Lucene学习-02”这一主题之前,我们先来理解一下Lucene的核心概念。Lucene是一个高性能、全文本搜索库,由Apache软件基金会开发,广泛应用于各种搜索引擎和信息检索系统。...

    Lucene.net学习帮助文档

    **Lucene.net学习帮助文档** Lucene.net是一个开源全文搜索引擎库,它是Apache Lucene项目的一部分,专门针对.NET Framework进行了优化。这个压缩包包含了Lucene.net的源码和中文学习文档,旨在帮助开发者深入理解...

    Lucene 3.6 学习笔记

    【Lucene 3.6 学习笔记】 Lucene 是一个高性能、全文本搜索库,广泛应用于各种搜索引擎的开发。本文将深入探讨Lucene 3.6版本中的关键概念、功能以及实现方法。 ### 第一章 Lucene 基础 #### 1.1 索引部分的核心...

    【大搜集:lucene学习资料】---<下载不扣分,回帖加1分,欢迎下载,童叟无欺>

    lucene学习笔记 1 .txt lucene学习笔记 2.txt lucene学习笔记 3 .txt lucene入门实战.txt Lucene 的学习 .txt Lucene-2.0学习文档 .txt Lucene入门与使用 .txt lucene性能.txt 大富翁全文索引和查询的例子...

    搜索引擎lucene学习资料

    通过这些学习资料,读者可以系统地学习搜索引擎的理论基础,掌握Lucene的核心功能,同时也能了解到如何在实际项目中应用这些技术,提升搜索系统的性能和用户体验。这些知识对于从事信息检索、网站开发、大数据分析等...

    Lucene学习工具包.zip

    **Lucene学习工具包** Lucene是一个开源的全文搜索引擎库,由Apache软件基金会开发并维护。这个"Lucene学习工具包.zip"包含了学习Lucene所需的重要资料和资源,旨在帮助开发者深入理解和掌握Lucene的核心概念、功能...

    lucene4.8学习资料和案例

    《Lucene 4.8学习指南与实战案例分析》 Lucene是一个强大的全文搜索引擎库,由Apache软件基金会开发,主要用于Java环境。版本4.8在功能和性能上都有显著提升,是许多开发者进行文本检索应用开发的重要工具。本文将...

    lucene学习总结

    **Lucene学习总结** 在深入理解Lucene之前,我们首先需要了解什么是全文检索。全文检索是一种从大量文本数据中快速查找所需信息的技术。它通过建立索引来实现高效的搜索,而Lucene正是Java环境下最著名的全文搜索...

Global site tag (gtag.js) - Google Analytics