Added infrastructure to figure out the number of unique values for a field on the atomic level and the highest number of atomic field values for all segments. This can use as a heuristic for initializing data structures.

Also moved the load method from concrete classes to AbstractIndexFieldData class.
This commit is contained in:
Martijn van Groningen 2013-08-15 19:24:02 +02:00
parent 1e7c0d69ff
commit c43d0d1746
15 changed files with 191 additions and 89 deletions

View File

@ -1,17 +1,22 @@
package org.elasticsearch.index.fielddata; package org.elasticsearch.index.fielddata;
import org.apache.lucene.index.AtomicReaderContext;
import org.apache.lucene.index.IndexReader; import org.apache.lucene.index.IndexReader;
import org.elasticsearch.ElasticSearchException;
import org.elasticsearch.common.settings.Settings; import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.index.AbstractIndexComponent; import org.elasticsearch.index.AbstractIndexComponent;
import org.elasticsearch.index.Index; import org.elasticsearch.index.Index;
import org.elasticsearch.index.mapper.FieldMapper; import org.elasticsearch.index.mapper.FieldMapper;
import org.elasticsearch.index.settings.IndexSettings; import org.elasticsearch.index.settings.IndexSettings;
import java.util.concurrent.atomic.AtomicLong;
/** /**
*/ */
public abstract class AbstractIndexFieldData<FD extends AtomicFieldData> extends AbstractIndexComponent implements IndexFieldData<FD> { public abstract class AbstractIndexFieldData<FD extends AtomicFieldData> extends AbstractIndexComponent implements IndexFieldData<FD> {
private final FieldMapper.Names fieldNames; private final FieldMapper.Names fieldNames;
private final AtomicLong highestUniqueValuesCount = new AtomicLong();
protected final FieldDataType fieldDataType; protected final FieldDataType fieldDataType;
protected final IndexFieldDataCache cache; protected final IndexFieldDataCache cache;
@ -36,4 +41,34 @@ public abstract class AbstractIndexFieldData<FD extends AtomicFieldData> extends
public void clear(IndexReader reader) { public void clear(IndexReader reader) {
cache.clear(reader); cache.clear(reader);
} }
@Override
public long getHighestNumberOfSeenUniqueValues() {
return highestUniqueValuesCount.get();
}
@Override
public final FD load(AtomicReaderContext context) {
try {
FD fd = cache.load(context, this);
updateHighestSeenValuesCount(fd.getNumberUniqueValues());
return fd;
} catch (Throwable e) {
if (e instanceof ElasticSearchException) {
throw (ElasticSearchException) e;
} else {
throw new ElasticSearchException(e.getMessage(), e);
}
}
}
private void updateHighestSeenValuesCount(long newValuesCount) {
long current;
do {
if ((current = highestUniqueValuesCount.get()) >= newValuesCount) {
break;
}
} while (!highestUniqueValuesCount.compareAndSet(current, newValuesCount));
}
} }

View File

@ -39,6 +39,11 @@ public interface AtomicFieldData<Script extends ScriptDocValues> {
*/ */
int getNumDocs(); int getNumDocs();
/**
* The number of unique values in this atomic field data.
*/
long getNumberUniqueValues();
/** /**
* Size (in bytes) of memory used by this field data. * Size (in bytes) of memory used by this field data.
*/ */

View File

@ -79,6 +79,11 @@ public interface IndexFieldData<FD extends AtomicFieldData> extends IndexCompone
void clear(IndexReader reader); void clear(IndexReader reader);
/**
* Returns the highest ever seen uniqiue values in an atomic reader.
*/
long getHighestNumberOfSeenUniqueValues();
// we need this extended source we we have custom comparators to reuse our field data // we need this extended source we we have custom comparators to reuse our field data
// in this case, we need to reduce type that will be used when search results are reduced // in this case, we need to reduce type that will be used when search results are reduced
// on another node (we don't have the custom source them...) // on another node (we don't have the custom source them...)

View File

@ -18,11 +18,13 @@
*/ */
package org.elasticsearch.index.fielddata.plain; package org.elasticsearch.index.fielddata.plain;
import org.apache.lucene.index.*; import org.apache.lucene.index.AtomicReader;
import org.apache.lucene.index.FilteredTermsEnum;
import org.apache.lucene.index.Terms;
import org.apache.lucene.index.TermsEnum;
import org.apache.lucene.util.BytesRef; import org.apache.lucene.util.BytesRef;
import org.apache.lucene.util.CharsRef; import org.apache.lucene.util.CharsRef;
import org.apache.lucene.util.UnicodeUtil; import org.apache.lucene.util.UnicodeUtil;
import org.elasticsearch.ElasticSearchException;
import org.elasticsearch.common.Nullable; import org.elasticsearch.common.Nullable;
import org.elasticsearch.common.settings.Settings; import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.index.Index; import org.elasticsearch.index.Index;
@ -55,19 +57,6 @@ public abstract class AbstractBytesIndexFieldData<FD extends AtomicFieldData.Wit
return true; return true;
} }
@Override
public FD load(AtomicReaderContext context) {
try {
return cache.load(context, this);
} catch (Throwable e) {
if (e instanceof ElasticSearchException) {
throw (ElasticSearchException) e;
} else {
throw new ElasticSearchException(e.getMessage(), e);
}
}
}
@Override @Override
public XFieldComparatorSource comparatorSource(@Nullable Object missingValue, SortMode sortMode) { public XFieldComparatorSource comparatorSource(@Nullable Object missingValue, SortMode sortMode) {
// TODO support "missingValue" for sortMissingValue options here... // TODO support "missingValue" for sortMissingValue options here...

View File

@ -77,6 +77,11 @@ public abstract class DoubleArrayAtomicFieldData extends AtomicNumericFieldData
return false; return false;
} }
@Override
public long getNumberUniqueValues() {
return 0;
}
@Override @Override
public long getMemorySizeInBytes() { public long getMemorySizeInBytes() {
return 0; return 0;
@ -114,6 +119,11 @@ public abstract class DoubleArrayAtomicFieldData extends AtomicNumericFieldData
return true; return true;
} }
@Override
public long getNumberUniqueValues() {
return ordinals.getNumOrds();
}
@Override @Override
public long getMemorySizeInBytes() { public long getMemorySizeInBytes() {
if (size == -1) { if (size == -1) {
@ -173,11 +183,13 @@ public abstract class DoubleArrayAtomicFieldData extends AtomicNumericFieldData
private final BigDoubleArrayList values; private final BigDoubleArrayList values;
private final FixedBitSet set; private final FixedBitSet set;
private final long numOrds;
public SingleFixedSet(BigDoubleArrayList values, int numDocs, FixedBitSet set) { public SingleFixedSet(BigDoubleArrayList values, int numDocs, FixedBitSet set, long numOrds) {
super(numDocs); super(numDocs);
this.values = values; this.values = values;
this.set = set; this.set = set;
this.numOrds = numOrds;
} }
@Override @Override
@ -190,6 +202,11 @@ public abstract class DoubleArrayAtomicFieldData extends AtomicNumericFieldData
return false; return false;
} }
@Override
public long getNumberUniqueValues() {
return numOrds;
}
@Override @Override
public long getMemorySizeInBytes() { public long getMemorySizeInBytes() {
if (size == -1) { if (size == -1) {
@ -260,14 +277,16 @@ public abstract class DoubleArrayAtomicFieldData extends AtomicNumericFieldData
public static class Single extends DoubleArrayAtomicFieldData { public static class Single extends DoubleArrayAtomicFieldData {
private final BigDoubleArrayList values; private final BigDoubleArrayList values;
private final long numOrds;
/** /**
* Note, here, we assume that there is no offset by 1 from docId, so position 0 * Note, here, we assume that there is no offset by 1 from docId, so position 0
* is the value for docId 0. * is the value for docId 0.
*/ */
public Single(BigDoubleArrayList values, int numDocs) { public Single(BigDoubleArrayList values, int numDocs, long numOrds) {
super(numDocs); super(numDocs);
this.values = values; this.values = values;
this.numOrds = numOrds;
} }
@Override @Override
@ -280,6 +299,11 @@ public abstract class DoubleArrayAtomicFieldData extends AtomicNumericFieldData
return false; return false;
} }
@Override
public long getNumberUniqueValues() {
return numOrds;
}
@Override @Override
public long getMemorySizeInBytes() { public long getMemorySizeInBytes() {
if (size == -1) { if (size == -1) {

View File

@ -23,7 +23,6 @@ import org.apache.lucene.index.AtomicReader;
import org.apache.lucene.index.AtomicReaderContext; import org.apache.lucene.index.AtomicReaderContext;
import org.apache.lucene.index.Terms; import org.apache.lucene.index.Terms;
import org.apache.lucene.util.*; import org.apache.lucene.util.*;
import org.elasticsearch.ElasticSearchException;
import org.elasticsearch.common.Nullable; import org.elasticsearch.common.Nullable;
import org.elasticsearch.common.settings.Settings; import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.common.util.BigDoubleArrayList; import org.elasticsearch.common.util.BigDoubleArrayList;
@ -65,19 +64,6 @@ public class DoubleArrayIndexFieldData extends AbstractIndexFieldData<DoubleArra
return false; return false;
} }
@Override
public DoubleArrayAtomicFieldData load(AtomicReaderContext context) {
try {
return cache.load(context, this);
} catch (Throwable e) {
if (e instanceof ElasticSearchException) {
throw (ElasticSearchException) e;
} else {
throw new ElasticSearchException(e.getMessage(), e);
}
}
}
@Override @Override
public DoubleArrayAtomicFieldData loadDirect(AtomicReaderContext context) throws Exception { public DoubleArrayAtomicFieldData loadDirect(AtomicReaderContext context) throws Exception {
@ -118,9 +104,9 @@ public class DoubleArrayIndexFieldData extends AbstractIndexFieldData<DoubleArra
} }
assert sValues.size() == maxDoc; assert sValues.size() == maxDoc;
if (set == null) { if (set == null) {
return new DoubleArrayAtomicFieldData.Single(sValues, maxDoc); return new DoubleArrayAtomicFieldData.Single(sValues, maxDoc, ordinals.getNumOrds());
} else { } else {
return new DoubleArrayAtomicFieldData.SingleFixedSet(sValues, maxDoc, set); return new DoubleArrayAtomicFieldData.SingleFixedSet(sValues, maxDoc, set, ordinals.getNumOrds());
} }
} else { } else {
return new DoubleArrayAtomicFieldData.WithOrdinals( return new DoubleArrayAtomicFieldData.WithOrdinals(

View File

@ -21,9 +21,11 @@ package org.elasticsearch.index.fielddata.plain;
import org.apache.lucene.util.BytesRef; import org.apache.lucene.util.BytesRef;
import org.apache.lucene.util.IntsRef; import org.apache.lucene.util.IntsRef;
import org.apache.lucene.util.fst.*; import org.apache.lucene.util.fst.BytesRefFSTEnum;
import org.apache.lucene.util.fst.FST;
import org.apache.lucene.util.fst.FST.Arc; import org.apache.lucene.util.fst.FST.Arc;
import org.apache.lucene.util.fst.FST.BytesReader; import org.apache.lucene.util.fst.FST.BytesReader;
import org.apache.lucene.util.fst.Util;
import org.elasticsearch.common.util.BigIntArray; import org.elasticsearch.common.util.BigIntArray;
import org.elasticsearch.index.fielddata.AtomicFieldData; import org.elasticsearch.index.fielddata.AtomicFieldData;
import org.elasticsearch.index.fielddata.ScriptDocValues; import org.elasticsearch.index.fielddata.ScriptDocValues;
@ -68,6 +70,11 @@ public class FSTBytesAtomicFieldData implements AtomicFieldData.WithOrdinals<Scr
return ordinals.getNumDocs(); return ordinals.getNumDocs();
} }
@Override
public long getNumberUniqueValues() {
return ordinals.getNumOrds();
}
@Override @Override
public boolean isValuesOrdered() { public boolean isValuesOrdered() {
return true; return true;

View File

@ -72,6 +72,11 @@ public abstract class FloatArrayAtomicFieldData extends AtomicNumericFieldData {
return false; return false;
} }
@Override
public long getNumberUniqueValues() {
return 0;
}
@Override @Override
public boolean isValuesOrdered() { public boolean isValuesOrdered() {
return false; return false;
@ -114,6 +119,11 @@ public abstract class FloatArrayAtomicFieldData extends AtomicNumericFieldData {
return true; return true;
} }
@Override
public long getNumberUniqueValues() {
return ordinals.getNumOrds();
}
@Override @Override
public long getMemorySizeInBytes() { public long getMemorySizeInBytes() {
if (size == -1) { if (size == -1) {
@ -171,11 +181,13 @@ public abstract class FloatArrayAtomicFieldData extends AtomicNumericFieldData {
private final BigFloatArrayList values; private final BigFloatArrayList values;
private final FixedBitSet set; private final FixedBitSet set;
private final long numOrd;
public SingleFixedSet(BigFloatArrayList values, int numDocs, FixedBitSet set) { public SingleFixedSet(BigFloatArrayList values, int numDocs, FixedBitSet set, long numOrd) {
super(numDocs); super(numDocs);
this.values = values; this.values = values;
this.set = set; this.set = set;
this.numOrd = numOrd;
} }
@Override @Override
@ -188,6 +200,11 @@ public abstract class FloatArrayAtomicFieldData extends AtomicNumericFieldData {
return false; return false;
} }
@Override
public long getNumberUniqueValues() {
return numOrd;
}
@Override @Override
public long getMemorySizeInBytes() { public long getMemorySizeInBytes() {
if (size == -1) { if (size == -1) {
@ -260,14 +277,16 @@ public abstract class FloatArrayAtomicFieldData extends AtomicNumericFieldData {
public static class Single extends FloatArrayAtomicFieldData { public static class Single extends FloatArrayAtomicFieldData {
private final BigFloatArrayList values; private final BigFloatArrayList values;
private final long numOrd;
/** /**
* Note, here, we assume that there is no offset by 1 from docId, so position 0 * Note, here, we assume that there is no offset by 1 from docId, so position 0
* is the value for docId 0. * is the value for docId 0.
*/ */
public Single(BigFloatArrayList values, int numDocs) { public Single(BigFloatArrayList values, int numDocs, long numOrd) {
super(numDocs); super(numDocs);
this.values = values; this.values = values;
this.numOrd = numOrd;
} }
@Override @Override
@ -280,6 +299,11 @@ public abstract class FloatArrayAtomicFieldData extends AtomicNumericFieldData {
return false; return false;
} }
@Override
public long getNumberUniqueValues() {
return numOrd;
}
@Override @Override
public long getMemorySizeInBytes() { public long getMemorySizeInBytes() {
if (size == -1) { if (size == -1) {

View File

@ -23,7 +23,6 @@ import org.apache.lucene.index.AtomicReader;
import org.apache.lucene.index.AtomicReaderContext; import org.apache.lucene.index.AtomicReaderContext;
import org.apache.lucene.index.Terms; import org.apache.lucene.index.Terms;
import org.apache.lucene.util.*; import org.apache.lucene.util.*;
import org.elasticsearch.ElasticSearchException;
import org.elasticsearch.common.Nullable; import org.elasticsearch.common.Nullable;
import org.elasticsearch.common.settings.Settings; import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.common.util.BigFloatArrayList; import org.elasticsearch.common.util.BigFloatArrayList;
@ -65,19 +64,6 @@ public class FloatArrayIndexFieldData extends AbstractIndexFieldData<FloatArrayA
return false; return false;
} }
@Override
public FloatArrayAtomicFieldData load(AtomicReaderContext context) {
try {
return cache.load(context, this);
} catch (Throwable e) {
if (e instanceof ElasticSearchException) {
throw (ElasticSearchException) e;
} else {
throw new ElasticSearchException(e.getMessage(), e);
}
}
}
@Override @Override
public FloatArrayAtomicFieldData loadDirect(AtomicReaderContext context) throws Exception { public FloatArrayAtomicFieldData loadDirect(AtomicReaderContext context) throws Exception {
AtomicReader reader = context.reader(); AtomicReader reader = context.reader();
@ -118,9 +104,9 @@ public class FloatArrayIndexFieldData extends AbstractIndexFieldData<FloatArrayA
} }
assert sValues.size() == maxDoc; assert sValues.size() == maxDoc;
if (set == null) { if (set == null) {
return new FloatArrayAtomicFieldData.Single(sValues, maxDoc); return new FloatArrayAtomicFieldData.Single(sValues, maxDoc, ordinals.getNumOrds());
} else { } else {
return new FloatArrayAtomicFieldData.SingleFixedSet(sValues, maxDoc, set); return new FloatArrayAtomicFieldData.SingleFixedSet(sValues, maxDoc, set, ordinals.getNumOrds());
} }
} else { } else {
return new FloatArrayAtomicFieldData.WithOrdinals( return new FloatArrayAtomicFieldData.WithOrdinals(

View File

@ -75,6 +75,11 @@ public abstract class GeoPointDoubleArrayAtomicFieldData extends AtomicGeoPointF
return false; return false;
} }
@Override
public long getNumberUniqueValues() {
return 0;
}
@Override @Override
public long getMemorySizeInBytes() { public long getMemorySizeInBytes() {
return 0; return 0;
@ -118,6 +123,11 @@ public abstract class GeoPointDoubleArrayAtomicFieldData extends AtomicGeoPointF
return true; return true;
} }
@Override
public long getNumberUniqueValues() {
return ordinals.getNumOrds();
}
@Override @Override
public long getMemorySizeInBytes() { public long getMemorySizeInBytes() {
if (size == -1) { if (size == -1) {
@ -253,12 +263,14 @@ public abstract class GeoPointDoubleArrayAtomicFieldData extends AtomicGeoPointF
private final BigDoubleArrayList lon, lat; private final BigDoubleArrayList lon, lat;
private final FixedBitSet set; private final FixedBitSet set;
private final long numOrds;
public SingleFixedSet(BigDoubleArrayList lon, BigDoubleArrayList lat, int numDocs, FixedBitSet set) { public SingleFixedSet(BigDoubleArrayList lon, BigDoubleArrayList lat, int numDocs, FixedBitSet set, long numOrds) {
super(numDocs); super(numDocs);
this.lon = lon; this.lon = lon;
this.lat = lat; this.lat = lat;
this.set = set; this.set = set;
this.numOrds = numOrds;
} }
@Override @Override
@ -271,6 +283,11 @@ public abstract class GeoPointDoubleArrayAtomicFieldData extends AtomicGeoPointF
return false; return false;
} }
@Override
public long getNumberUniqueValues() {
return numOrds;
}
@Override @Override
public long getMemorySizeInBytes() { public long getMemorySizeInBytes() {
if (size == -1) { if (size == -1) {
@ -351,11 +368,13 @@ public abstract class GeoPointDoubleArrayAtomicFieldData extends AtomicGeoPointF
public static class Single extends GeoPointDoubleArrayAtomicFieldData { public static class Single extends GeoPointDoubleArrayAtomicFieldData {
private final BigDoubleArrayList lon, lat; private final BigDoubleArrayList lon, lat;
private final long numOrds;
public Single(BigDoubleArrayList lon, BigDoubleArrayList lat, int numDocs) { public Single(BigDoubleArrayList lon, BigDoubleArrayList lat, int numDocs, long numOrds) {
super(numDocs); super(numDocs);
this.lon = lon; this.lon = lon;
this.lat = lat; this.lat = lat;
this.numOrds = numOrds;
} }
@Override @Override
@ -368,6 +387,11 @@ public abstract class GeoPointDoubleArrayAtomicFieldData extends AtomicGeoPointF
return false; return false;
} }
@Override
public long getNumberUniqueValues() {
return numOrds;
}
@Override @Override
public long getMemorySizeInBytes() { public long getMemorySizeInBytes() {
if (size == -1) { if (size == -1) {

View File

@ -23,7 +23,6 @@ import org.apache.lucene.index.AtomicReader;
import org.apache.lucene.index.AtomicReaderContext; import org.apache.lucene.index.AtomicReaderContext;
import org.apache.lucene.index.Terms; import org.apache.lucene.index.Terms;
import org.apache.lucene.util.*; import org.apache.lucene.util.*;
import org.elasticsearch.ElasticSearchException;
import org.elasticsearch.ElasticSearchIllegalArgumentException; import org.elasticsearch.ElasticSearchIllegalArgumentException;
import org.elasticsearch.common.Nullable; import org.elasticsearch.common.Nullable;
import org.elasticsearch.common.settings.Settings; import org.elasticsearch.common.settings.Settings;
@ -60,19 +59,6 @@ public class GeoPointDoubleArrayIndexFieldData extends AbstractIndexFieldData<Ge
return false; return false;
} }
@Override
public GeoPointDoubleArrayAtomicFieldData load(AtomicReaderContext context) {
try {
return cache.load(context, this);
} catch (Throwable e) {
if (e instanceof ElasticSearchException) {
throw (ElasticSearchException) e;
} else {
throw new ElasticSearchException(e.getMessage(), e);
}
}
}
@Override @Override
public GeoPointDoubleArrayAtomicFieldData loadDirect(AtomicReaderContext context) throws Exception { public GeoPointDoubleArrayAtomicFieldData loadDirect(AtomicReaderContext context) throws Exception {
AtomicReader reader = context.reader(); AtomicReader reader = context.reader();
@ -119,9 +105,9 @@ public class GeoPointDoubleArrayIndexFieldData extends AbstractIndexFieldData<Ge
} }
FixedBitSet set = builder.buildDocsWithValuesSet(); FixedBitSet set = builder.buildDocsWithValuesSet();
if (set == null) { if (set == null) {
return new GeoPointDoubleArrayAtomicFieldData.Single(sLon, sLat, reader.maxDoc()); return new GeoPointDoubleArrayAtomicFieldData.Single(sLon, sLat, reader.maxDoc(), ordinals.getNumOrds());
} else { } else {
return new GeoPointDoubleArrayAtomicFieldData.SingleFixedSet(sLon, sLat, reader.maxDoc(), set); return new GeoPointDoubleArrayAtomicFieldData.SingleFixedSet(sLon, sLat, reader.maxDoc(), set, ordinals.getNumOrds());
} }
} else { } else {
return new GeoPointDoubleArrayAtomicFieldData.WithOrdinals( return new GeoPointDoubleArrayAtomicFieldData.WithOrdinals(

View File

@ -83,6 +83,11 @@ public abstract class PackedArrayAtomicFieldData extends AtomicNumericFieldData
return 0; return 0;
} }
@Override
public long getNumberUniqueValues() {
return 0;
}
@Override @Override
public BytesValues getBytesValues() { public BytesValues getBytesValues() {
return BytesValues.EMPTY; return BytesValues.EMPTY;
@ -123,6 +128,11 @@ public abstract class PackedArrayAtomicFieldData extends AtomicNumericFieldData
return size; return size;
} }
@Override
public long getNumberUniqueValues() {
return ordinals.getNumOrds();
}
@Override @Override
public LongValues getLongValues() { public LongValues getLongValues() {
return new LongValues(values, ordinals.ordinals()); return new LongValues(values, ordinals.ordinals());
@ -175,12 +185,14 @@ public abstract class PackedArrayAtomicFieldData extends AtomicNumericFieldData
private final PackedInts.Mutable values; private final PackedInts.Mutable values;
private final long minValue; private final long minValue;
private final long missingValue; private final long missingValue;
private final long numOrds;
public SingleSparse(PackedInts.Mutable values, long minValue, int numDocs, long missingValue) { public SingleSparse(PackedInts.Mutable values, long minValue, int numDocs, long missingValue, long numOrds) {
super(numDocs); super(numDocs);
this.values = values; this.values = values;
this.minValue = minValue; this.minValue = minValue;
this.missingValue = missingValue; this.missingValue = missingValue;
this.numOrds = numOrds;
} }
@Override @Override
@ -193,6 +205,11 @@ public abstract class PackedArrayAtomicFieldData extends AtomicNumericFieldData
return false; return false;
} }
@Override
public long getNumberUniqueValues() {
return numOrds;
}
@Override @Override
public long getMemorySizeInBytes() { public long getMemorySizeInBytes() {
if (size == -1) { if (size == -1) {
@ -270,15 +287,17 @@ public abstract class PackedArrayAtomicFieldData extends AtomicNumericFieldData
private final PackedInts.Mutable values; private final PackedInts.Mutable values;
private final long minValue; private final long minValue;
private final long numOrds;
/** /**
* Note, here, we assume that there is no offset by 1 from docId, so position 0 * Note, here, we assume that there is no offset by 1 from docId, so position 0
* is the value for docId 0. * is the value for docId 0.
*/ */
public Single(PackedInts.Mutable values, long minValue, int numDocs) { public Single(PackedInts.Mutable values, long minValue, int numDocs, long numOrds) {
super(numDocs); super(numDocs);
this.values = values; this.values = values;
this.minValue = minValue; this.minValue = minValue;
this.numOrds = numOrds;
} }
@Override @Override
@ -291,6 +310,11 @@ public abstract class PackedArrayAtomicFieldData extends AtomicNumericFieldData
return false; return false;
} }
@Override
public long getNumberUniqueValues() {
return numOrds;
}
@Override @Override
public long getMemorySizeInBytes() { public long getMemorySizeInBytes() {
if (size == -1) { if (size == -1) {

View File

@ -29,7 +29,6 @@ import org.apache.lucene.util.FixedBitSet;
import org.apache.lucene.util.NumericUtils; import org.apache.lucene.util.NumericUtils;
import org.apache.lucene.util.packed.MonotonicAppendingLongBuffer; import org.apache.lucene.util.packed.MonotonicAppendingLongBuffer;
import org.apache.lucene.util.packed.PackedInts; import org.apache.lucene.util.packed.PackedInts;
import org.elasticsearch.ElasticSearchException;
import org.elasticsearch.common.Nullable; import org.elasticsearch.common.Nullable;
import org.elasticsearch.common.settings.Settings; import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.index.Index; import org.elasticsearch.index.Index;
@ -85,19 +84,6 @@ public class PackedArrayIndexFieldData extends AbstractIndexFieldData<AtomicNume
return false; return false;
} }
@Override
public AtomicNumericFieldData load(AtomicReaderContext context) {
try {
return cache.load(context, this);
} catch (Throwable e) {
if (e instanceof ElasticSearchException) {
throw (ElasticSearchException) e;
} else {
throw new ElasticSearchException(e.getMessage(), e);
}
}
}
@Override @Override
public AtomicNumericFieldData loadDirect(AtomicReaderContext context) throws Exception { public AtomicNumericFieldData loadDirect(AtomicReaderContext context) throws Exception {
AtomicReader reader = context.reader(); AtomicReader reader = context.reader();
@ -184,9 +170,9 @@ public class PackedArrayIndexFieldData extends AbstractIndexFieldData<AtomicNume
} }
} }
if (set == null) { if (set == null) {
return new PackedArrayAtomicFieldData.Single(sValues, minValue, reader.maxDoc()); return new PackedArrayAtomicFieldData.Single(sValues, minValue, reader.maxDoc(), ordinals.getNumOrds());
} else { } else {
return new PackedArrayAtomicFieldData.SingleSparse(sValues, minValue, reader.maxDoc(), missingValue); return new PackedArrayAtomicFieldData.SingleSparse(sValues, minValue, reader.maxDoc(), missingValue, ordinals.getNumOrds());
} }
} else { } else {
return new PackedArrayAtomicFieldData.WithOrdinals(values, reader.maxDoc(), build); return new PackedArrayAtomicFieldData.WithOrdinals(values, reader.maxDoc(), build);

View File

@ -68,6 +68,11 @@ public class PagedBytesAtomicFieldData implements AtomicFieldData.WithOrdinals<S
return ordinals.getNumDocs(); return ordinals.getNumDocs();
} }
@Override
public long getNumberUniqueValues() {
return ordinals.getNumOrds();
}
@Override @Override
public boolean isValuesOrdered() { public boolean isValuesOrdered() {
return true; return true;
@ -265,6 +270,11 @@ public class PagedBytesAtomicFieldData implements AtomicFieldData.WithOrdinals<S
return ordinals.getNumDocs(); return ordinals.getNumDocs();
} }
@Override
public long getNumberUniqueValues() {
return 0;
}
@Override @Override
public boolean isValuesOrdered() { public boolean isValuesOrdered() {
return true; return true;

View File

@ -34,7 +34,6 @@ import org.elasticsearch.index.fielddata.IndexFieldData;
import org.elasticsearch.index.fielddata.fieldcomparator.SortMode; import org.elasticsearch.index.fielddata.fieldcomparator.SortMode;
import org.junit.Test; import org.junit.Test;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.*; import static org.hamcrest.Matchers.*;
/** /**
@ -103,8 +102,10 @@ public abstract class AbstractStringFieldDataTests extends AbstractFieldDataTest
IndexFieldData indexFieldData = getForField("value"); IndexFieldData indexFieldData = getForField("value");
AtomicReaderContext readerContext = refreshReader(); AtomicReaderContext readerContext = refreshReader();
AtomicFieldData fieldData = indexFieldData.load(readerContext); AtomicFieldData fieldData = indexFieldData.load(readerContext);
assertThat(indexFieldData.getHighestNumberOfSeenUniqueValues(), greaterThan(0l));
BytesValues values = fieldData.getBytesValues(); BytesValues values = fieldData.getBytesValues();
assertThat(fieldData.getNumDocs(), equalTo(2)); assertThat(fieldData.getNumDocs(), equalTo(2));
assertThat(fieldData.getNumberUniqueValues(), equalTo(2l));
for (int i = 0; i < fieldData.getNumDocs(); ++i) { for (int i = 0; i < fieldData.getNumDocs(); ++i) {
assertThat(values.hasValue(i), equalTo(true)); assertThat(values.hasValue(i), equalTo(true));
} }
@ -117,6 +118,8 @@ public abstract class AbstractStringFieldDataTests extends AbstractFieldDataTest
AtomicReaderContext readerContext = refreshReader(); AtomicReaderContext readerContext = refreshReader();
AtomicFieldData fieldData = indexFieldData.load(readerContext); AtomicFieldData fieldData = indexFieldData.load(readerContext);
assertThat(fieldData.getMemorySizeInBytes(), greaterThan(0l)); assertThat(fieldData.getMemorySizeInBytes(), greaterThan(0l));
assertThat(fieldData.getNumberUniqueValues(), equalTo(3l));
assertThat(indexFieldData.getHighestNumberOfSeenUniqueValues(), greaterThan(0l));
assertThat(fieldData.getNumDocs(), equalTo(3)); assertThat(fieldData.getNumDocs(), equalTo(3));
@ -211,6 +214,8 @@ public abstract class AbstractStringFieldDataTests extends AbstractFieldDataTest
AtomicFieldData fieldData = indexFieldData.load(refreshReader()); AtomicFieldData fieldData = indexFieldData.load(refreshReader());
assertThat(fieldData.getMemorySizeInBytes(), greaterThan(0l)); assertThat(fieldData.getMemorySizeInBytes(), greaterThan(0l));
assertThat(fieldData.getNumberUniqueValues(), equalTo(2l));
assertThat(indexFieldData.getHighestNumberOfSeenUniqueValues(), greaterThan(0l));
assertThat(fieldData.getNumDocs(), equalTo(3)); assertThat(fieldData.getNumDocs(), equalTo(3));
BytesValues bytesValues = fieldData BytesValues bytesValues = fieldData
@ -291,6 +296,8 @@ public abstract class AbstractStringFieldDataTests extends AbstractFieldDataTest
assertThat(fieldData.getMemorySizeInBytes(), greaterThan(0l)); assertThat(fieldData.getMemorySizeInBytes(), greaterThan(0l));
assertThat(fieldData.getNumDocs(), equalTo(3)); assertThat(fieldData.getNumDocs(), equalTo(3));
assertThat(fieldData.getNumberUniqueValues(), equalTo(4l));
assertThat(indexFieldData.getHighestNumberOfSeenUniqueValues(), greaterThan(0l));
BytesValues bytesValues = fieldData.getBytesValues(); BytesValues bytesValues = fieldData.getBytesValues();
@ -379,6 +386,8 @@ public abstract class AbstractStringFieldDataTests extends AbstractFieldDataTest
assertThat(fieldData.getMemorySizeInBytes(), greaterThan(0l)); assertThat(fieldData.getMemorySizeInBytes(), greaterThan(0l));
assertThat(fieldData.getNumDocs(), equalTo(3)); assertThat(fieldData.getNumDocs(), equalTo(3));
assertThat(fieldData.getNumberUniqueValues(), equalTo(3l));
assertThat(indexFieldData.getHighestNumberOfSeenUniqueValues(), greaterThan(0l));
BytesValues bytesValues = fieldData.getBytesValues(); BytesValues bytesValues = fieldData.getBytesValues();
@ -440,6 +449,8 @@ public abstract class AbstractStringFieldDataTests extends AbstractFieldDataTest
assertThat(fieldData.getMemorySizeInBytes(), greaterThanOrEqualTo(0l)); assertThat(fieldData.getMemorySizeInBytes(), greaterThanOrEqualTo(0l));
assertThat(fieldData.getNumDocs(), equalTo(3)); assertThat(fieldData.getNumDocs(), equalTo(3));
assertThat(fieldData.getNumberUniqueValues(), equalTo(0l));
assertThat(indexFieldData.getHighestNumberOfSeenUniqueValues(), equalTo(0l));
BytesValues bytesValues = fieldData.getBytesValues(); BytesValues bytesValues = fieldData.getBytesValues();