`
JavaStudyEye
  • 浏览: 80604 次
  • 性别: Icon_minigender_1
  • 来自: 上海
社区版块
存档分类
最新评论

如何搞定 lucene3.0 自定义排序

阅读更多
本文引言: 利用别人的东西写东西,最好看别人的源码!   思路最重要!



自定义排序思路:继承FieldComparatorSource类并在此类的newComparator方法中返回一个FieldComparator类的子类

可以参考lucene的org.apache.lucene.search.FieldComparator.StringValComparator
类的源码,自己做做实验 就搞定啦!



背景:初始化自定义排序类的时候,其构造方法我这里有两个参数,但是可以有多个的,我们首先用总行数(总行数是我们自己设定的,
我们在TopDocs topDocs = indexSearcher.search(query, null, 3004, sort);这句话中 的第三个参数就是了。如果结果集总数小于我们设定的总个数,则按照结果集总数来确定)初始化values数组,用 Field的name值来初始化自定义排序类里面的field属性,这个属性lucene用来拿到相关的数据集
 
  1、setNextReader : lucene首先会调用此方法进行数据的初始化,我们这里用一个String数组currentReaderValues来接收,当然也可以用其他的,如float,这个大家可以慢慢用FieldCache.DEFAULT.getStrings(reader, this.field);这句话来试。或者 直接debug 看看里面的东西,就OK! 看API描述 "Set a new Reader"
  2、copy : 第一次将currentReaderValues里面的两个值拿出来,以后都是一个,然后放到values(注意初始时此数组的值都是null)中的指定位置上看API描述 "This method is called when a new hit is competitive"
 
  3、compare :自定义排序 我们可以将我们的代码写到这里,看PAI描述" Compare hit at slot1 with hit at slot2." ,解释一下slot2 和 slot1 是索引文件中的索引号,注意slot1的值大于slot2的值,也就是说 val1为后一个的值,val2为前一个的值
看API描述 "Compare hit at slot1 with hit at slot2." 
 
  4、compareBottom :看API描述"Compare the bottom of the queue with doc." 这个方法lucene时候调用呢,从描述来看是doc序列的尾部,呵呵,自定义排序列中的bottom属性值就是,我们要拿出来的序列中最后面的那个。 流程是: 如果优先队列满了,则先和最低层的比较,如果大于最底层的则先替代最底层的,然后对优先队列重新排序 ,队列的最大值是 通过ndexSearcher.search方法中可以设置的,当然 lucene的队列的长度最大值 我看了 应该是 2亿多。所以不用担心了。那么对列什么时候满了呢?队列的最大值是什么呢?答案是: 队列的最大值 由用户自己设定,TopDocs topDocs = indexSearcher.search(query, null, 3004, sort);这句话中 的第三个参数就是了




package com;

import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Date;

import org.apache.lucene.index.IndexReader;
import org.apache.lucene.search.FieldCache;
import org.apache.lucene.search.FieldComparator;
import org.apache.lucene.search.FieldComparatorSource;

//这里继承FieldComparatorSource类 ,然后返回DateValComparator的自定义子类,并传递两个参数
public class MySortComparatorSource extends FieldComparatorSource {

	private static final long serialVersionUID = 1L;

	@Override
	public FieldComparator newComparator(String field, int allCounts,
			int newCount, boolean reversed) throws IOException {
		
		//打印出来大家就知道了
		System.out.println(field);
		System.out.println(allCounts);
		System.out.println(newCount);
		System.out.println(reversed);
		//第一个参数是 总行数,第二个参数是 field的name值。就是需要比较的name值,例如 "createDate"
		return new DateValComparator(allCounts, field);
	}

}

//我们自定义排序类DateValComparator 继承FieldComparator 类实现里面的方法

final class DateValComparator extends FieldComparator {
	private String[] values;
	private String[] currentReaderValues;
	private final String field;
	private String bottom;
	SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
	
	DateValComparator(int numHits, String field) {
		this.values = new String[numHits];
		this.field = field;
	}

	//第三步调用的比较方法,如果查询结果没有超过超过了我们设定的总行数那么会调用这个方法进行比较
	public int compare(int slot1, int slot2) {
		try {
			Date val1 = format.parse(this.values[slot1]);
			Date val2 = format.parse(this.values[slot2]);
			if(null == val1) {
				if(null == val2) {
					return 0;
				}
				return -1;
			}
			if(null == val2) {
				return 1;
			}
			
			if(val1.after(val2)) {
				return 1;
			} 
			if(val2.after(val1)) {
				return -1;
			}
			
		} catch(Exception e) {
			e.printStackTrace();
		}
		
		return 0;
	}

	//Lucene的查询结果是放在优先队列里面的,优先对象是通过compare进行比较,如果查询结果超过了我们设定的总行数那么会第二步调用这个方法
	public int compareBottom(int doc) {
		try {
			Date val2 = format.parse(this.currentReaderValues[doc]);
			Date tempBottom = format.parse(this.bottom);
			if (tempBottom == null) {
				if (val2 == null) {
					return 0;
				}
				return -1;
			}
			if (val2 == null) {
				return 1;
			}
			if(val2.after(tempBottom)) {
				return 1;
			} 
			if(tempBottom.after(val2)) {
				return -1;
			}
		} catch(Exception e) {
			e.printStackTrace();
		}
			return 0;
	}

	//第二步调用的方法,将currentReaderValues时间数组中的第一个值 copy到 values中对应的位置中,注意此方法第一次调用了两次
	public void copy(int slot, int doc) {
		this.values[slot] = this.currentReaderValues[doc];
	}

	// 第一步调用的方法: 本方法是得到所有搜索到的时间数组并初始化currentValues,docBase用来确定需要几个数组
	public void setNextReader(IndexReader reader, int docBase) throws IOException {
		this.currentReaderValues = FieldCache.DEFAULT.getStrings(reader, this.field);
	}
	
	//如果查询结果超过了我们设定的总行数那么会第一步调用这个方法
	public void setBottom(int bottom) {
		this.bottom = this.values[bottom];
	}

	//要输出的拍好序的结果集
	public Comparable value(int slot) {
		return this.values[slot];
	}

}





最后在 lucene主方法中 引用一下就Ok,如下代码

//按照时间的正序排列,如果SortField的第三个参数为true , 则为倒序
SortField sortField = new SortField("createDate", new MySortComparatorSource(), true);
Sort sort = new Sort ();  
sort.setSort(sortField);
TopDocs topDocs = indexSearcher.search(query, null, 1000, sort); //这里的第三个参数要注意,设定将要返回结果集的长度。
ScoreDoc[] scoreDocs = topDocs.scoreDocs;


写的 很匆忙,,继续留个备用。。。 “唯有努力”










分享到:
评论
2 楼 a953924393 2014-06-17  
太给力了,虽然已经几年了,还是找到我想要的。
1 楼 abcstring 2011-12-10  
不错 备用一下

相关推荐

    lucene3.0核心jar包

    在 Lucene 3.0 中,还支持评分函数和自定义排序。 6. **优化与更新**:索引的优化(Merge)操作可以合并多个段以减少磁盘空间占用和提高搜索性能。同时,Lucene 3.0 支持对已有索引的增删改操作,但需要注意的是,...

    Lucene 3.0 原理与代码分析完整版

    《Lucene 3.0 原理与代码分析完整版》是一本深入解析Lucene 3.0搜索引擎库的专业书籍。Lucene是Apache软件基金会的开源项目,它为Java开发者提供了一个高性能、全文检索的工具包,广泛应用于各种信息检索系统。这...

    lucene3.0庖丁+索引搜索程序

    此外,还可以自定义排序规则,如基于文档评分或自定义元数据。 三、索引搜索程序实践 在“NewestPaoding”文件中,包含了使用Lucene3.0进行索引搜索的代码示例。这通常包括以下步骤: 1. 创建索引:首先,我们...

    lucene3.0使用介绍及实例

    在本文中,我们将深入探讨Lucene 3.0版本,了解其核心概念、功能特性,并通过实例来展示如何使用这个强大的工具。 ### 1. Lucene 3.0核心概念 #### 1.1 文档与字段 在Lucene中,数据是以文档(Document)的形式...

    lucene3.0 search

    《深入解析Lucene 3.0搜索技术》 在信息技术高速发展的今天,搜索引擎已经成为人们获取信息、解决问题的重要工具。作为开源全文检索库的代表,Apache Lucene为开发者提供了强大的文本检索功能,使得构建高效、精准...

    Lucene3.0做的文件搜索

    **Lucene3.0文件搜索概述** Lucene是Apache软件基金会的一个开源全文搜索引擎库,它提供了高级的文本分析和索引功能,使开发者能够轻松地在应用中实现强大的搜索功能。在Lucene 3.0版本中,这个功能得到了进一步...

    关于全文检索的文章(使用技术Lucene3.0)

    3. **结果排序**: Lucene支持多种评分机制,如TF-IDF(词频-逆文档频率),可以根据评分对搜索结果进行排序。 4. **优化索引**: 可以定期进行索引合并,以减少索引分段数量,提高搜索性能。 **源码分析** 由于...

    lucene3.0-api.CHM

    5. 排序与过滤:除了基于评分的排序外,还可以根据自定义字段进行排序。Filter类允许在搜索时应用过滤条件。 总结,Lucene 3.0 API提供了一套完整的框架,用于构建高效的全文搜索引擎。开发者可以通过这个API对文本...

    lucene3.0学习笔记(三)与paoding整合

    首先,Lucene是一个高性能、全文检索库,提供了完整的搜索功能,包括索引、查询、排序等。版本3.0是其发展过程中的一个重要里程碑,它引入了诸多改进和优化,如更快的索引速度、更高效的查询处理以及更好的内存管理...

    lucene 3.0 例子

    4. **评分与排序(Scoring and Sorting)**:Lucene根据相关性对搜索结果进行评分,示例可能会展示如何获取和理解这些分数,以及如何根据其他字段(如日期或自定义评分函数)进行排序。 5. **结果集(Result Set)*...

    Apache Lucene3.0 入门实例介绍

    这个入门实例将引导我们了解如何使用Lucene 3.0版本进行基本的索引和搜索操作。以下是对Lucene 3.0关键知识点的详细讲解: 1. **Lucene的架构**: Lucene的核心组件包括文档(Document)、字段(Field)、索引...

    Lucene_3.0_原理与代码分析

    ### Lucene 3.0 原理与代码分析 #### 一、全文检索基本原理 全文检索(Full-text Search)是一种从非结构化文本中提取相关信息的技术,它允许用户通过输入关键词来查找文档中是否包含这些关键词。全文检索系统通常...

    Lucene+3.0+原理与代码分析完整版

    Lucene 提供了多种内置的分词器,同时也支持自定义分词器。 #### 有关Lucene的问题解析 1. **“中华AND共和国”与“中华共和国”的区别**:由于Lucene默认使用标准分词器,它会将连续的字母数字序列视为一个词条,...

    Lucene3.0.3+盘古分词 资源汇总

    Lucene的核心功能包括文档的索引、搜索以及相关性排序。它提供了一个简单的API,允许开发者对文本进行索引,并通过搜索接口快速找到相关的文档。Lucene 3.0.3是一个相对稳定的版本,尽管较新的版本可能包含更多的...

    Lucence3.0学习

    《深入探索Lucene 3.0:源码与工具篇》 Lucene是Apache软件基金会的一个开源项目,它提供了一个高性能、全文检索的API,使得开发者可以轻易地在自己的应用中实现复杂的全文检索功能。本篇文章将围绕Lucene 3.0版本...

    盘古分词、lucene3.0.3搜索的使用示例v1.2

    6. **结果展示**:最后,将搜索结果以用户友好的方式呈现出来,如按相关度排序,展示文档摘要等。 在这个示例项目中,`SearchTest.sln`是解决方案文件,包含了项目的整体结构;`SearchTest.suo`是Visual Studio的...

Global site tag (gtag.js) - Google Analytics