com.browseengine.bobo.facets.impl.GeoFacetHandler Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of bobo-browse Show documentation
Show all versions of bobo-browse Show documentation
Bobo is a Faceted Search implementation written purely in Java, an extension of Apache Lucene
The newest version!
/**
*
*/
package com.browseengine.bobo.facets.impl;
import java.io.IOException;
import java.util.Arrays;
import java.util.HashSet;
import java.util.List;
import java.util.Properties;
import com.browseengine.bobo.api.BoboSegmentReader;
import com.browseengine.bobo.api.BrowseSelection;
import com.browseengine.bobo.api.FacetSpec;
import com.browseengine.bobo.facets.FacetCountCollector;
import com.browseengine.bobo.facets.FacetCountCollectorSource;
import com.browseengine.bobo.facets.FacetHandler;
import com.browseengine.bobo.facets.data.FacetDataCache;
import com.browseengine.bobo.facets.data.TermValueList;
import com.browseengine.bobo.facets.filter.GeoFacetFilter;
import com.browseengine.bobo.facets.filter.RandomAccessFilter;
import com.browseengine.bobo.facets.impl.GeoFacetCountCollector.GeoRange;
import com.browseengine.bobo.sort.DocComparatorSource;
import com.browseengine.bobo.util.BigFloatArray;
import com.browseengine.bobo.util.BigSegmentedArray;
import com.browseengine.bobo.util.GeoMatchUtil;
/** Constructor for GeoFacetHandler
* @param name - name of the Geo facet
*
*/
public class GeoFacetHandler extends FacetHandler {
private final String _latFieldName;
private final String _lonFieldName;
// variable to specify if the geo distance calculations are in miles. Default is miles
private boolean _miles;
public GeoFacetHandler(String name, String latFieldName, String lonFieldName) {
super(name, new HashSet(Arrays.asList(new String[] { latFieldName, lonFieldName })));
_latFieldName = latFieldName;
_lonFieldName = lonFieldName;
_miles = true;
}
/**
* Constructor for GeoFacetHandler
* @param name name of the geo facet
* @param latFieldName name of the index field that stores the latitude value
* @param lonFieldName name of the index field that stores the longitude value
* @param miles variable to specify if the geo distance calculations are in miles. False indicates distance calculation is in kilometers
*/
public GeoFacetHandler(String name, String latFieldName, String lonFieldName, boolean miles) {
this(name, latFieldName, lonFieldName);
_miles = miles;
}
public static class GeoFacetData {
private BigFloatArray _xValArray;
private BigFloatArray _yValArray;
private BigFloatArray _zValArray;
public GeoFacetData() {
_xValArray = null;
_yValArray = null;
_zValArray = null;
}
public GeoFacetData(BigFloatArray xvals, BigFloatArray yvals, BigFloatArray zvals) {
_xValArray = xvals;
_yValArray = yvals;
_zValArray = zvals;
}
public static BigFloatArray newInstance(int maxDoc) {
BigFloatArray array = new BigFloatArray(maxDoc);
array.ensureCapacity(maxDoc);
return array;
}
/**
* @return the _xValArray
*/
public BigFloatArray get_xValArray() {
return _xValArray;
}
/**
* @param xValArray the _xValArray to set
*/
public void set_xValArray(BigFloatArray xValArray) {
_xValArray = xValArray;
}
/**
* @return the _yValArray
*/
public BigFloatArray get_yValArray() {
return _yValArray;
}
/**
* @param yValArray the _yValArray to set
*/
public void set_yValArray(BigFloatArray yValArray) {
_yValArray = yValArray;
}
/**
* @return the _zValArray
*/
public BigFloatArray get_zValArray() {
return _zValArray;
}
/**
* @param zValArray the _zValArray to set
*/
public void set_zValArray(BigFloatArray zValArray) {
_zValArray = zValArray;
}
public void load(String latFieldName, String lonFieldName, BoboSegmentReader reader)
throws IOException {
if (reader == null) throw new IOException("reader object is null");
FacetDataCache> latCache = (FacetDataCache>) reader.getFacetData(latFieldName);
FacetDataCache> lonCache = (FacetDataCache>) reader.getFacetData(lonFieldName);
int maxDoc = reader.maxDoc();
BigFloatArray xVals = this._xValArray;
BigFloatArray yVals = this._yValArray;
BigFloatArray zVals = this._zValArray;
if (xVals == null) xVals = newInstance(maxDoc);
else xVals.ensureCapacity(maxDoc);
if (yVals == null) yVals = newInstance(maxDoc);
else yVals.ensureCapacity(maxDoc);
if (zVals == null) zVals = newInstance(maxDoc);
else zVals.ensureCapacity(maxDoc);
this._xValArray = xVals;
this._yValArray = yVals;
this._zValArray = zVals;
BigSegmentedArray latOrderArray = latCache.orderArray;
TermValueList> latValList = latCache.valArray;
BigSegmentedArray lonOrderArray = lonCache.orderArray;
TermValueList> lonValList = lonCache.valArray;
for (int i = 0; i < maxDoc; ++i) {
String docLatString = latValList.get(latOrderArray.get(i)).trim();
String docLonString = lonValList.get(lonOrderArray.get(i)).trim();
float docLat = 0;
if (docLatString.length() > 0) {
docLat = Float.parseFloat(docLatString);
}
float docLon = 0;
if (docLonString.length() > 0) {
docLon = Float.parseFloat(docLonString);
}
float[] coords = GeoMatchUtil.geoMatchCoordsFromDegrees(docLat, docLon);
_xValArray.add(i, coords[0]);
_yValArray.add(i, coords[1]);
_zValArray.add(i, coords[2]);
}
}
}
/**
* Builds a random access filter.
* @param value Should be of the form: lat, lon: rad
* @param selectionProperty
*/
@Override
public RandomAccessFilter buildRandomAccessFilter(String value, Properties selectionProperty)
throws IOException {
GeoRange range = GeoFacetCountCollector.parse(value);
return new GeoFacetFilter(this, range.getLat(), range.getLon(), range.getRad(), _miles);
}
@Override
public DocComparatorSource getDocComparatorSource() {
throw new UnsupportedOperationException("Doc comparator not yet supported for Geo Facets");
}
@Override
public FacetCountCollectorSource getFacetCountCollectorSource(final BrowseSelection sel,
final FacetSpec fspec) {
return new FacetCountCollectorSource() {
final List ranges = Arrays.asList(sel.getValues());
@Override
public FacetCountCollector getFacetCountCollector(BoboSegmentReader reader, int docBase) {
GeoFacetData dataCache = getFacetData(reader);
return new GeoFacetCountCollector(_name, dataCache, docBase, fspec, ranges, _miles);
}
};
}
@Override
public String[] getFieldValues(BoboSegmentReader reader, int id) {
GeoFacetData dataCache = getFacetData(reader);
BigFloatArray xvals = dataCache.get_xValArray();
BigFloatArray yvals = dataCache.get_yValArray();
BigFloatArray zvals = dataCache.get_zValArray();
float xvalue = xvals.get(id);
float yvalue = yvals.get(id);
float zvalue = zvals.get(id);
float lat = GeoMatchUtil.getMatchLatDegreesFromXYZCoords(xvalue, yvalue, zvalue);
float lon = GeoMatchUtil.getMatchLonDegreesFromXYZCoords(xvalue, yvalue, zvalue);
String[] fieldValues = new String[2];
fieldValues[0] = String.valueOf(lat);
fieldValues[1] = String.valueOf(lon);
return fieldValues;
}
@Override
public GeoFacetData load(BoboSegmentReader reader) throws IOException {
GeoFacetData dataCache = new GeoFacetData();
dataCache.load(_latFieldName, _lonFieldName, reader);
return dataCache;
}
}