001/* 002 AUTOMATICALLY GENERATED BY jTemp FROM 003 /Users/jsh2/Work/openimaj/target/checkout/core/core-feature/src/main/jtemp/org/openimaj/feature/#T#FV.jtemp 004*/ 005/** 006 * Copyright (c) 2011, The University of Southampton and the individual contributors. 007 * All rights reserved. 008 * 009 * Redistribution and use in source and binary forms, with or without modification, 010 * are permitted provided that the following conditions are met: 011 * 012 * * Redistributions of source code must retain the above copyright notice, 013 * this list of conditions and the following disclaimer. 014 * 015 * * Redistributions in binary form must reproduce the above copyright notice, 016 * this list of conditions and the following disclaimer in the documentation 017 * and/or other materials provided with the distribution. 018 * 019 * * Neither the name of the University of Southampton nor the names of its 020 * contributors may be used to endorse or promote products derived from this 021 * software without specific prior written permission. 022 * 023 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND 024 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 025 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 026 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR 027 * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 028 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 029 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON 030 * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 031 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 032 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 033 */ 034package org.openimaj.feature; 035 036import java.io.DataInput; 037import java.io.DataOutput; 038import java.io.IOException; 039import java.io.PrintWriter; 040import java.util.Arrays; 041import java.util.List; 042import java.util.Scanner; 043 044import org.openimaj.util.concatenate.Concatenatable; 045 046/** 047 * Basic long single-dimensional feature vector implementation 048 * 049 * @author Jonathon Hare 050 */ 051public class LongFV extends ArrayFeatureVector<long[]> implements Concatenatable<LongFV, LongFV>, Cloneable { 052 private static final long serialVersionUID = 1L; 053 054 /** 055 * Construct an empty feature vector 056 */ 057 public LongFV() {} 058 059 /** 060 * Construct empty FV with given number of bins 061 * @param nbins the number of bins in each dimension 062 */ 063 public LongFV(int nbins) { 064 values = new long[nbins]; 065 } 066 067 /** 068 * Construct from flattened values array and dimensions 069 * @param values the flat array of values 070 */ 071 public LongFV(long [] values) { 072 this.values = values; 073 } 074 075 /** 076 * Get the element at the given flat index 077 * @param x the flattened element index 078 * @return the value corresponding to x 079 */ 080 public long get(int x) { 081 return values[x]; 082 } 083 084 /** 085 * Set the element at the given flat index 086 * @param value the value to set 087 * @param x the flattened element index 088 */ 089 void set(long value, int x) { 090 values[x] = value; 091 } 092 093 /** 094 * Element-wise normalisation to 0..1 using separated expected 095 * minimum and maximum values for each element of the underlying 096 * feature vector. 097 * 098 * @param min an array containing the minimum expected values 099 * @param max an array containing the maximum expected values 100 * @return feature vector with each value normalised to 0..1 101 */ 102 @Override 103 public DoubleFV normaliseFV(double [] min, double [] max) { 104 double [] dvals = asDoubleVector(); 105 106 for (int i=0; i<dvals.length; i++) { 107 dvals[i] -= min[i]; 108 dvals[i] /= (max[i]-min[i]); 109 110 if (dvals[i]<0) dvals[i] = 0; 111 if (dvals[i]>1) dvals[i] = 1; 112 } 113 114 return new DoubleFV(dvals); 115 } 116 117 /** 118 * Min-Max normalisation of the FV. Each element of the underlying 119 * feature vector is normalised to 0..1 based on the provided 120 * minimum and maximum expected values. 121 * 122 * @param min the minimum expected value 123 * @param max the maximum expected value 124 * @return feature vector with each value normalised to 0..1 125 */ 126 @Override 127 public DoubleFV normaliseFV(double min, double max) { 128 double [] dvals = asDoubleVector(); 129 130 for (int i=0; i<dvals.length; i++) { 131 dvals[i] -= min; 132 dvals[i] /= (max-min); 133 134 if (dvals[i]<0) dvals[i] = 0; 135 if (dvals[i]>1) dvals[i] = 1; 136 } 137 138 return new DoubleFV(dvals); 139 } 140 141 /** 142 * Normalise the FV to unit area. 143 * 144 * @return feature vector with all elements summing to 1. 145 */ 146 @Override 147 public DoubleFV normaliseFV() { 148 double [] dvals = asDoubleVector(); 149 double sum = 0; 150 151 for (int i=0; i<dvals.length; i++) 152 sum += dvals[i]; 153 154 for (int i=0; i<dvals.length; i++) 155 dvals[i] /= sum; 156 157 return new DoubleFV(dvals); 158 } 159 160 /** 161 * Lp Norm of the FV. 162 * 163 * @param 164 * p the norm to compute 165 * 166 * @return feature vector normalised using the Lp norm 167 */ 168 @Override 169 public DoubleFV normaliseFV(double p) { 170 double [] dvals = asDoubleVector(); 171 double pnorm = 0; 172 173 for (int i=0; i<dvals.length; i++) 174 pnorm += Math.pow(Math.abs(dvals[i]), p); 175 176 pnorm = Math.pow(pnorm, 1.0 / p); 177 178 for (int i=0; i<dvals.length; i++) 179 dvals[i] /= pnorm; 180 181 return new DoubleFV(dvals); 182 } 183 184 @Override 185 public LongFV clone() { 186 try { 187 LongFV model = (LongFV) super.clone(); 188 model.values = values.clone(); 189 return model; 190 }catch (CloneNotSupportedException e) { 191 throw new AssertionError(e); 192 } 193 } 194 195 @Override 196 public String toString() { 197 String ret = this.getClass().getName() + Arrays.toString(values); 198 199 return ret; 200 } 201 202 /** 203 * Convert the FV to a DoubleFV representation 204 * @return the DoubleFV representation 205 */ 206 @Override 207 public DoubleFV asDoubleFV() { 208 return new DoubleFV(asDoubleVector()); 209 } 210 211 /** 212 * Convert the FV to a 1-dimensional double array representation 213 * @return the double[] representation 214 */ 215 @Override 216 public double [] asDoubleVector() { 217 double [] d = new double[values.length]; 218 219 for (int i=0; i<values.length; i++) { 220 d[i] = values[i]; 221 } 222 223 return d; 224 } 225 226 /** 227 * Compare this FV to another with the given method. 228 * 229 * @param h the feature to compare against. 230 * @param method the method to compare with. 231 * @return a score determined by the comparison method. 232 */ 233 public double compare(LongFV h, LongFVComparison method) { 234 return method.compare(this, h); 235 } 236 237 /* (non-Javadoc) 238 * @see org.openimaj.feature.FeatureVector#length() 239 */ 240 @Override 241 public int length() { 242 return values.length; 243 } 244 245 @Override 246 public void writeBinary(DataOutput out) throws IOException { 247 out.writeInt(values.length); 248 for (int i=0; i<values.length; i++) out.writeLong(values[i]); 249 } 250 251 @Override 252 public void writeASCII(PrintWriter out) throws IOException { 253 out.println(values.length); 254 for (int i=0; i<values.length; i++) out.print( values[i] + " "); 255 out.println(); 256 } 257 258 @Override 259 public void readBinary(DataInput in) throws IOException { 260 int nbins = in.readInt(); 261 values = new long[nbins]; 262 for (int i=0; i<nbins; i++) values[i] = in.readLong(); 263 } 264 265 @Override 266 public void readASCII(Scanner in) throws IOException { 267 int nbins = Integer.parseInt(in.nextLine()); 268 values = new long[nbins]; 269 String [] line = in.nextLine().trim().split(" "); 270 for (int i=0; i<nbins; i++) values[i] = Long.parseLong(line[i]); 271 } 272 273 @Override 274 public byte[] binaryHeader() { 275 return (this.getClass().getName().substring(0,2) + "FV").getBytes(); 276 } 277 278 @Override 279 public String asciiHeader() { 280 return this.getClass().getName() + " "; 281 } 282 283 @Override 284 public LongFV concatenate(LongFV... ins) { 285 int l = values.length; 286 287 for (int i=0; i<ins.length; i++) 288 l += ins[i].values.length; 289 290 long[] data = new long[l]; 291 292 System.arraycopy(values, 0, data, 0, values.length); 293 int offset = values.length; 294 for (int i=0; i<ins.length; i++) { 295 System.arraycopy(ins[i].values, 0, data, offset, ins[i].values.length); 296 offset += ins[i].values.length; 297 } 298 299 return new LongFV(data); 300 } 301 302 @Override 303 public LongFV concatenate(List<LongFV> ins) { 304 int l = values.length; 305 306 for (int i=0; i<ins.size(); i++) 307 l += ins.get(i).values.length; 308 309 long[] data = new long[l]; 310 311 System.arraycopy(values, 0, data, 0, values.length); 312 int offset = values.length; 313 for (int i=0; i<ins.size(); i++) { 314 System.arraycopy(ins.get(i).values, 0, data, offset, ins.get(i).values.length); 315 offset += ins.get(i).values.length; 316 } 317 318 return new LongFV(data); 319 } 320 321 @Override 322 public int hashCode() { 323 return Arrays.hashCode(values); 324 } 325 326 @Override 327 public boolean equals(Object obj) { 328 return Arrays.equals(values, ((LongFV)obj).values); 329 } 330 331 @Override 332 public LongFV subvector(int beginIndex) { 333 return new LongFV(Arrays.copyOfRange(this.values, beginIndex, values.length)); 334 } 335 336 @Override 337 public LongFV subvector(int beginIndex, int endIndex) { 338 return new LongFV(Arrays.copyOfRange(this.values, beginIndex, endIndex)); 339 } 340 341 @Override 342 public double getAsDouble(int i) { 343 return values[i]; 344 } 345 346 @Override 347 public void setFromDouble(int i, double v) { 348 values[i] = ((long) v); 349 } 350 351 @Override 352 public LongFV newInstance() { 353 return new LongFV(length()); 354 } 355}