package joshua.discriminative.semiring_parsing; public class ExpectationSemiringVector implements CompositeSemiring{ // TODO: assuming the following are always in *log* semiring private double logProb; //TODO: assuming the following are always in *real* semiring private SignedValue[] factor1; int vectorSize; public ExpectationSemiringVector(int vectorSize_){ vectorSize= vectorSize_; factor1 = new SignedValue[vectorSize]; for(int i=0; i<factor1.length; i++) factor1[i] = new SignedValue(); } public ExpectationSemiringVector(double logProb_, SignedValue[] factor1_){ logProb = logProb_; factor1 = factor1_; vectorSize = factor1.length; } public void setToZero(AtomicSemiring atomic){ logProb = atomic.ATOMIC_ZERO_IN_SEMIRING; for(int i=0; i<vectorSize; i++){ factor1[i].setZero(); } } public void setToOne(AtomicSemiring atomic){ logProb = atomic.ATOMIC_ONE_IN_SEMIRING; /**Note that factor should always set as zero. * For example, when the factor is expected length, it should start from zero * */ for(int i=0; i<vectorSize; i++){ factor1[i].setZero(); } } public void add(CompositeSemiring b, AtomicSemiring atomic){ ExpectationSemiringVector b2 = (ExpectationSemiringVector)b; this.logProb = atomic.add_in_atomic_semiring(this.logProb, b2.logProb); for(int i=0; i<vectorSize; i++){ this.factor1[i] = SignedValue.add(this.factor1[i], b2.factor1[i]); } } public void multi(CompositeSemiring b, AtomicSemiring atomic){ ExpectationSemiringVector b2 = (ExpectationSemiringVector)b; for(int i=0; i<vectorSize; i++){ //this.factor1[i] = Math.exp(oldLogProb)* b2.factor1[i] + Math.exp(b2.logProb) * oldFactor1[i]; this.factor1[i] = SignedValue.add( SignedValue.multi(this.logProb, b2.factor1[i]), SignedValue.multi(b2.logProb, this.factor1[i]) ); } this.logProb = atomic.multi_in_atomic_semiring(this.logProb, b2.logProb); } public void normalizeFactors(){ /**we should not normalize the probability at each intermediate node * because our model is a global model??? */ /**originallly, the factor value is \sum_x p(x).v(x), where p(x) is not normalized, meaning \sum_x p(x)!=1; * we need to normalize p(x) by divide out Math.exp(prob) * */ for(int i=0; i<vectorSize; i++){ //this.factor1[i] = factor1[i]/Math.exp(logProb); this.factor1[i] = SignedValue.multi(-logProb, this.factor1[i]); } } public void printInfor(){ System.out.println("prob: " + logProb ); System.out.print("factor1:"); for(int i=0; i<vectorSize; i++){ System.out.print(" " + factor1[i].convertRealValue()); } System.out.print("\n"); } public void printInfor2(){ SignedValue[] true_factor1 = new SignedValue[vectorSize]; for(int i=0; i<vectorSize; i++){ true_factor1[i] = SignedValue.multi(-logProb, this.factor1[i]); } System.out.println("prob: " + logProb + "; factor1: " + factor1 + "; factor2: " + factor1); System.out.println("true factor1: " + true_factor1 + "; true factor2: " + true_factor1); } public double getLogProb(){ return logProb; } public SignedValue[] getFactor1(){ return factor1; } }