package shared.filt; import shared.DataSet; import shared.Instance; import util.linalg.Matrix; import util.linalg.RectangularMatrix; import util.linalg.SingularValueDecomposition; /** * A filter that performs a random projection * @author Andrew Guillory gtg008g@mail.gatech.edu * @version 1.0 */ public class RandomizedProjectionFilter implements ReversibleFilter { /** * The projection itself */ private Matrix projection; /** * Make a new random projection * @param componentsToKeep the number of components to keep * @param components the number of original components */ public RandomizedProjectionFilter(int componentsOut, int componentsIn){ projection = RectangularMatrix.random(componentsOut, componentsIn); projection.minusEquals(RectangularMatrix.ones(projection.m(), projection.n()).times(.5)); SingularValueDecomposition svd = new SingularValueDecomposition(projection); if (componentsIn <= componentsOut) { projection = svd.getU().get(0,projection.m(),0,projection.n()); } else { projection = svd.getV().get(0,projection.m(),0,projection.n()); } } /** * @see shared.filt.DataSetFilter#filter(shared.DataSet) */ public void filter(DataSet dataSet) { for (int i = 0; i < dataSet.size(); i++) { Instance instance = dataSet.get(i); instance.setData(projection.times(instance.getData())); } } /** * @see shared.filt.ReversibleFilter#reverse(shared.DataSet) */ public void reverse(DataSet dataSet) { for (int i = 0; i < dataSet.size(); i++) { Instance instance = dataSet.get(i); instance.setData(projection.transpose().times(instance.getData())); } } /** * Get the projection * @return the projection */ public Matrix getProjection() { return projection; } }