Spatial for Lucene4.x Example

package com.nnn.c.test;


import java.io.File;
import java.io.IOException;


import org.apache.lucene.analysis.cn.smart.SmartChineseAnalyzer;
import org.apache.lucene.document.Document;
import org.apache.lucene.document.Field;
import org.apache.lucene.document.IntField;
import org.apache.lucene.document.StoredField;
import org.apache.lucene.document.TextField;
import org.apache.lucene.index.DirectoryReader;
import org.apache.lucene.index.IndexReader;
import org.apache.lucene.index.IndexWriter;
import org.apache.lucene.index.IndexWriterConfig;
import org.apache.lucene.index.IndexableField;
import org.apache.lucene.index.Term;
import org.apache.lucene.search.Filter;
import org.apache.lucene.search.IndexSearcher;
import org.apache.lucene.search.Query;
import org.apache.lucene.search.ScoreDoc;
import org.apache.lucene.search.TermQuery;
import org.apache.lucene.search.TopDocs;
import org.apache.lucene.spatial.SpatialStrategy;
import org.apache.lucene.spatial.prefix.RecursivePrefixTreeStrategy;
import org.apache.lucene.spatial.prefix.tree.GeohashPrefixTree;
import org.apache.lucene.spatial.prefix.tree.SpatialPrefixTree;
import org.apache.lucene.spatial.query.SpatialArgs;
import org.apache.lucene.spatial.query.SpatialOperation;
import org.apache.lucene.store.Directory;
import org.apache.lucene.store.FSDirectory;
import org.apache.lucene.util.Version;


import com.nnn.m.service.SpatialUtils;
import com.spatial4j.core.context.SpatialContext;
import com.spatial4j.core.distance.DistanceUtils;
import com.spatial4j.core.shape.Shape;


public class LuceneSpatialExample {


public static void main(String[] args) throws IOException {
new LuceneSpatialExample().test();
}


public void test() throws IOException {
init();
createIndex();
search();
}


private SpatialContext ctx;// "ctx" is the conventional variable name


private SpatialStrategy strategy;


private Directory directory;


private String indexPath = "E:\\index\\spatial\\";


protected void init() {
// Typical geospatial context
// These can also be constructed from SpatialContextFactory
this.ctx = SpatialContext.GEO;


int maxLevels = 11;// results in sub-meter precision for geohash
// This can also be constructed from SpatialPrefixTreeFactory
SpatialPrefixTree grid = new GeohashPrefixTree(ctx, maxLevels);


this.strategy = new RecursivePrefixTreeStrategy(grid, "myGeoField");


try {
this.directory = FSDirectory.open(new File(indexPath));
} catch (IOException e) {
e.printStackTrace();
}
}


private void createIndex() throws IOException {
IndexWriterConfig iwConfig = new IndexWriterConfig(Version.LUCENE_48, new SmartChineseAnalyzer(Version.LUCENE_48));
IndexWriter indexWriter = new IndexWriter(directory, iwConfig);
// Spatial4j is x-y order for arguments|对于参数的顺序是Longitude,Latitude
indexWriter.addDocument(newSampleDocument(0, "一星大饭店", ctx.makePoint(116.430360, 39.939686)));
indexWriter.addDocument(newSampleDocument(1, "二星大饭店", ctx.makePoint(116.430319, 39.939702)));
indexWriter.addDocument(newSampleDocument(2, "三星大饭店", ctx.makePoint(116.430459, 39.939802)));
indexWriter.addDocument(newSampleDocument(3, "四星大饭店", ctx.makePoint(116.430449, 39.939902)));
indexWriter.addDocument(newSampleDocument(4, "六星大饭店", ctx.makePoint(116.430439, 39.93402)));
indexWriter.addDocument(newSampleDocument(5, "七星大饭店", ctx.makePoint(116.430419, 39.939802)));
indexWriter.addDocument(newSampleDocument(6, "五星大饭店", ctx.makePoint(116.430429, 39.934202)));
indexWriter.addDocument(newSampleDocument(6, "五星大酒店", ctx.makePoint(115.430429, 39.934202)));
indexWriter.commit();
indexWriter.close();
}


private Document newSampleDocument(int id, String keyword, Shape... shapes) {
Document doc = new Document();
doc.add(new IntField("id", id, Field.Store.YES));
// Potentially more than one shape in this field is supported by some
// strategies; see the javadocs of the SpatialStrategy impl to see.
for (Shape shape : shapes) {
for (IndexableField f : strategy.createIndexableFields(shape)) {
doc.add(f);
}
// store it too; the format is up to you
doc.add(new StoredField(strategy.getFieldName(), ctx.toString(shape)));
}
doc.add(new TextField("keyword", keyword, Field.Store.YES));
return doc;
}


private void search() throws IOException {
IndexReader indexReader = DirectoryReader.open(directory);
IndexSearcher indexSearcher = new IndexSearcher(indexReader);
{
// 16米范围内
SpatialArgs args = new SpatialArgs(SpatialOperation.Intersects, ctx.makeCircle(116.430459, 39.939802,
DistanceUtils.dist2Degrees(0.016, DistanceUtils.EARTH_MEAN_RADIUS_KM)));
Filter filter = strategy.makeFilter(args);
Term term = new Term("keyword", "饭店");
Query query001 = new TermQuery(term);


TopDocs docs = indexSearcher.search(query001, filter, 1000);
System.out.println(docs.totalHits);


ScoreDoc[] scoreDoc = docs.scoreDocs;
if (docs.totalHits > 0)
for (int i = 0; i < scoreDoc.length; i++) {
int doc = scoreDoc[i].doc;
Document mydoc = indexReader.document(doc);
System.out.println(mydoc.get("myGeoField"));
String value = mydoc.get("myGeoField");
String[] lonlat = value.split(" ");
double eLat = Double.valueOf(lonlat[1]);
double eLon = Double.valueOf(lonlat[0]);
System.out.println(SpatialUtils.getDistance(39.939802, 116.430459, eLat, eLon) + "|keyword: " + mydoc.get("keyword"));
}
}
indexReader.close();
}


}


运行结果:
4
116.430360 39.939686
12.0|keyword: 一星大饭店
116.430459 39.939802
0.0|keyword: 三星大饭店
116.430449 39.939902
5.0|keyword: 四星大饭店
116.430419 39.939802
4.0|keyword: 七星大饭店
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值