package mikera.vectorz.impl; import mikera.indexz.GrowableIndex; import mikera.indexz.Index; import mikera.vectorz.AVector; import mikera.vectorz.GrowableVector; import mikera.vectorz.util.VectorzException; /** * Implementation for a sparse indexed vector that can accumulate index/value pairs efficiently (in order) * @author Mike */ public class GrowableIndexedVector extends ASparseVector { private static final long serialVersionUID = 441979517032171392L; private final GrowableIndex index; private final GrowableVector data; private GrowableIndexedVector(int length, GrowableIndex index, GrowableVector data) { super(length); this.index=index; this.data=data; } private GrowableIndexedVector(int length) { super(length); this.index=new GrowableIndex(); this.data=new GrowableVector(); } public static GrowableIndexedVector createLength(int len) { return new GrowableIndexedVector(len); } @Override public double get(int i) { checkIndex(i); int ix=index.indexPosition(i); if (ix<0) return 0.0; return data.get(ix); } public void append(int i, double value) { index.checkedAppend(i); data.append(value); } @Override public void set(int i, double value) { int ix=index.indexPosition(i); if (ix<0) throw new UnsupportedOperationException("Can't set at index: "+i); data.unsafeSet(ix, value); } @Override public boolean isFullyMutable() { // TODO: consider making fully mutable? return false; } @Override public double dotProduct(double[] data, int offset) { return toSparseIndexedVector().dotProduct(data,offset); } public SparseIndexedVector toSparseIndexedVector() { return SparseIndexedVector.create(length, Index.create(index), data.toDoubleArray()); } @Override public AVector exactClone() { return new GrowableIndexedVector(length,index.exactClone(), data.exactClone()); } @Override public SparseIndexedVector sparseClone() { return toSparseIndexedVector(); } @Override public int nonSparseElementCount() { return index.length(); } @Override public AVector nonSparseValues() { return data; } @Override public Index nonSparseIndex() { return Index.create(index); } @Override public boolean includesIndex(int i) { return index.indexPosition(i)>=0; } @Override public void add(ASparseVector v) { Index ix=v.nonSparseIndex(); AVector vs=v.nonSparseValues(); int n=ix.length(); for (int i=0; i<n; i++) { addAt(ix.get(i),vs.get(i)); } } @Override public void validate() { if (index.length()!=data.length()) throw new VectorzException("Mismatched index and data length!"); } }