下面给出一段 可直接跑通 的 Lucene 8.5.0 示例代码,演示如何
1. 建索引时为两个字段启用 DocValues(一个 `NumericDocValues`,一个 `SortedDocValues`);
2. 用 `IndexSearcher` 按 DocValues 排序;
3. 用 `FacetsCollector` 做分组统计(相当于 SQL 的 `GROUP BY`)。
```java
import org.apache.lucene.analysis.standard.StandardAnalyzer;
import org.apache.lucene.codecs.lucene50.Lucene50Codec;
import org.apache.lucene.document.*;
import org.apache.lucene.index.*;
import org.apache.lucene.search.*;
import org.apache.lucene.store.ByteBuffersDirectory;
import org.apache.lucene.util.NumericUtils;
import org.apache.lucene.facet.*;
import org.apache.lucene.facet.sortedset.SortedSetDocValuesFacetCounts;
import org.apache.lucene.facet.sortedset.SortedSetDocValuesFacetField;
public class DocValuesDemo {
public static void main(String[] args) throws Exception {
/* ---------- 1. 创建内存目录 ---------- */
Directory dir = new ByteBuffersDirectory();
IndexWriterConfig cfg = new IndexWriterConfig(new StandardAnalyzer());
// 使用默认 codec 即可,DocValues 默认开启
cfg.setCodec(new Lucene50Codec());
IndexWriter writer = new IndexWriter(dir, cfg);
/* ---------- 2. 写入三条示范文档 ---------- */
Document doc1 = new Document();
doc1.add(new StringField("id", "1", Field.Store.YES));
// 商品价:NumericDocValues,可排序、可聚合
doc1.add(new NumericDocValuesField("price", 2999));
// 商品品牌:SortedDocValues,可做 faceting
doc1.add(new SortedSetDocValuesFacetField("brand", "小米"));
Document doc2 = new Document();
doc2.add(new StringField("id", "2", Field.Store.YES));
doc2.add(new NumericDocValuesField("price", 3999));
doc2.add(new SortedSetDocValuesFacetField("brand", "苹果"));
Document doc3 = new Document();
doc3.add(new StringField("id", "3", Field.Store.YES));
doc3.add(new NumericDocValuesField("price", 1999));
doc3.add(new SortedSetDocValuesFacetField("brand", "小米"));
writer.addDocument(doc1);
writer.addDocument(doc2);
writer.addDocument(doc3);
writer.commit();
writer.close();
/* ---------- 3. 打开搜索器 ---------- */
DirectoryReader reader = DirectoryReader.open(dir);
IndexSearcher searcher = new IndexSearcher(reader);
/* ---------- 4. 按价格升序排序 ---------- */
Sort sort = new Sort(new SortField("price", SortField.Type.LONG));
TopDocs topDocs = searcher.search(new MatchAllDocsQuery(), 10, sort);
for (ScoreDoc sd : topDocs.scoreDocs) {
Document d = searcher.doc(sd.doc);
System.out.println("id=" + d.get("id"));
}
// 输出:
// id=3 (1999)
// id=1 (2999)
// id=2 (3999)
/* ---------- 5. 用 Facets 统计品牌分布 ---------- */
FacetsCollector fc = new FacetsCollector();
searcher.search(new MatchAllDocsQuery(), fc

最低0.47元/天 解锁文章
1086

被折叠的 条评论
为什么被折叠?



