您的位置:首页 > 其它

Lucene全文搜索学习笔记(二)

2017-01-15 21:00 387 查看

个人笔记之用,如有错误,恳请批评指正。

LuceneUtil的编写,主要是对document2bean以及bean2document操作的封装。写的不完善,先学完Lucene再说。

public class LuceneUtil {
private static Directory directory;
private static Version version;
private static Analyzer analyzer;
private static MaxFieldLength maxFieldLength;
static{
try {
directory = FSDirectory.open(new File("F:/java/practice/luceneDir"));
version = Version.LUCENE_30;
analyzer = new StandardAnalyzer(version);
maxFieldLength = MaxFieldLength.LIMITED;
} catch (Exception e) {
e.printStackTrace();
}
}

/**
*
* @param obj 传入的对象,用到反射将Field存入索引库
* @return doc对象
* @throws Exception
*/
public static Document bean2document(Object obj) throws Exception{
/*
* 思路:document.add(new Field(name,content,Store?,Index?))
* 利用反射获取传入的obj中name属性对应的content
* */
Document document = new Document();
Class clazz = obj.getClass();
Field[] fields = clazz.getDeclaredFields();
//对传入的obj每个field遍历,利用get方法取出值并存入索引库
for (Field field : fields) {
field.setAccessible(true);
String getMethodName = "get"+field.getName().substring(0,1).toUpperCase()+field.getName().substring(1);
Method method = clazz.getDeclaredMethod(getMethodName, null);
String fieldValue = "";
if(method.invoke(obj, null)!=null){
fieldValue = method.invoke(obj, null).toString();//参数1:执行的对象,参数2:所需的参数
}
document.add(new org.apache.lucene.document.Field(field.getName(), fieldValue, Store.YES, Index.ANALYZED));//两种Field
}
return document;
}
/**
*
* @param document
* @param clazz 返回的Class
* @return
* @throws Exception
*/
public static Object document2bean(Document document,Class clazz) throws Exception{
/*
* 思路 :BeanUtils.setProperty(obj,name,value);
**/
Object obj = clazz.newInstance();
Field[] fields = clazz.getDeclaredFields();
for (Field field : fields) {
field.setAccessible(true);
String name = field.getName();
BeanUtils.setProperty(obj, name, document.get(name).toString());//参数1:对象. 参数2:变量名
4000
.参数3:变量值
}
return obj;
}

public static Directory getDirectory() {
return directory;
}
public static Version getVersion() {
return version;
}
public static Analyzer getAnalyzer() {
return analyzer;
}
public static MaxFieldLength getMaxFieldLength() {
return maxFieldLength;
}
}


Lucene的增删改查:

public class LuceneCRUD {

public void addIndexDB(Object obj){
try {
Document document = LuceneUtil.bean2document(obj);
IndexWriter indexWriter = new IndexWriter(LuceneUtil.getDirectory(), LuceneUtil.getAnalyzer(), LuceneUtil.getMaxFieldLength());
indexWriter.addDocument(document);
indexWriter.close();
} catch (Exception e) {
e.printStackTrace();
}
}

public void updateIndexDB(Object obj){
try {
Document document = LuceneUtil.bean2document(obj);
IndexWriter indexWriter = new IndexWriter(LuceneUtil.getDirectory(), LuceneUtil.getAnalyzer(), LuceneUtil.getMaxFieldLength());
//Term表示需要更新的document对象。id用户找到该document。在这里先写死。
indexWriter.updateDocument(new Term("id","1"), document);
indexWriter.close();
} catch (Exception e) {
e.printStackTrace();
}
}

public void deleteAllIndexDB(){
try {
IndexWriter indexWriter = new IndexWriter(LuceneUtil.getDirectory(), LuceneUtil.getAnalyzer(), LuceneUtil.getMaxFieldLength());
indexWriter.deleteAll();
indexWriter.close();
} catch (Exception e) {
e.printStackTrace();
}
}
public void deleteIndexDB(){
try {
IndexWriter indexWriter = new IndexWriter(LuceneUtil.getDirectory(), LuceneUtil.getAnalyzer(), LuceneUtil.getMaxFieldLength());
indexWriter.deleteDocuments(new Term("id","1"));// 删除id为1的doc
indexWriter.close();
} catch (Exception e) {
e.printStackTrace();
}
}

public void searchIndexDB(String keyword){
try {
IndexSearcher indexSearcher = new IndexSearcher(LuceneUtil.getDirectory());
QueryParser queryParser = new QueryParser(Version.LUCENE_30, "content", LuceneUtil.getAnalyzer());
Query query = queryParser.parse(keyword);
TopDocs topDocs = indexSearcher.search(query, 5);
ScoreDoc[] scoreDocs = topDocs.scoreDocs;
for (ScoreDoc scoreDoc : scoreDocs) {
Document doc = indexSearcher.doc(scoreDoc.doc);
Article article = (Article) LuceneUtil.document2bean(doc, Article.class);
System.out.println(article.getTitle()+":"+article.getContent());
}
} catch (Exception e) {
e.printStackTrace();
}
}
@Test
public void testAdd(){
addIndexDB(new Article(1,"标题","内容"));
}
@Test
public void testDelete(){
deleteIndexDB();
}
@Test
public void testDeleteAll(){
deleteAllIndexDB();
}
@Test
public void testSearch(){
searchIndexDB("");
}
@Test
public void testUpdate(){
updateIndexDB(new Article(1,"新标题2","好!"));
}
}


分页的初步实现:

public class LuceneDaoImpl {

public List<Article> selectArticlePage(String keyword,int pageIndex,int pageSize){
List<Article> list = new ArrayList<Article>();
IndexSearcher indexSearcher = null;
try {
int start = (pageIndex-1)*pageSize;
int end = pageIndex*pageSize;

QueryParser queryParser = new QueryParser(Version.LUCENE_30,"title", LuceneUtil.getAnalyzer());
Query query = queryParser.parse(keyword);
indexSearcher = new IndexSearcher(LuceneUtil.getDirectory());
TopDocs topDocs = indexSearcher.search(query, end);
System.out.println("总记录数为:"+topDocs.totalHits);

//总记录数小于end,说明scoreDocs不满end条。即返回的是start--totalHits条。否则返回的是start--end条
ScoreDoc[] scoreDocs = topDocs.scoreDocs;
int size = end;
if(topDocs.totalHits<end) {
size = topDocs.totalHits;
}
if(topDocs.totalHits<=start){
System.out.println("没有记录了!");
return null;
}
for(int i = start ;i<size;i++){
Document doc = indexSearcher.doc(scoreDocs[i].doc);
Article article = (Article) LuceneUtil.document2bean(doc,Article.class);
list.add(article);
}
} catch (Exception e) {
e.printStackTrace();
}finally{
try {
indexSearcher.close();
} catch (Exception e) {
e.printStackTrace();
}
}
return list;
}
@Test
public void testSearchPage(){
int pageIndex = 1;
int pageSize = 19;
List<Article> list = selectArticlePage("标题", pageIndex, pageSize);
if(list!=null){
System.out.println(list.size());
for (Article article : list) {
System.out.println(article.getTitle()+":"+article.getContent());
}
System.out.println("第"+pageIndex+"页"+"每页"+pageSize+"条");
}
}
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: