MorphicVectorTransformer.java

package edu.udel.cis.vsl.tass.morph;

import java.util.HashMap;
import java.util.Map;

public class MorphicVectorTransformer<T extends Morphic> implements
		MorphicTransformerIF<MorphicVector<T>> {


	private MorphicVectorFactory<T> vectorFactory;

	private MorphicTransformerIF<T> elementTransformer;

	private Map<MorphicVector<T>, MorphicVector<T>> cache = new HashMap<MorphicVector<T>, MorphicVector<T>>();

	public MorphicVectorTransformer(MorphicVectorFactory<T> vectorFactory,
			MorphicTransformerIF<T> elementTransformer) {
		this.vectorFactory = vectorFactory;
		this.elementTransformer = elementTransformer;
	}

	@Override
	public MorphicVector<T> transform(MorphicVector<T> vector) {
		MorphicVector<T> newVector;

		vector = vectorFactory.canonic(vector);
		newVector = cache.get(vector);
		if (newVector != null)
			return newVector;

		int length = vector.size();

		for (int i = 0; i < length; i++) {
			T oldValue = vector.get(i);

			if (oldValue != null) {
				T newValue = elementTransformer.transform(oldValue);

				if (newValue != oldValue) {
					if (newVector == null) {
						newVector = vectorFactory.newVector(length);
						for (int j = 0; j < i; j++)
							newVector.set(j, vector.get(j));
					}
					newVector.set(i, newValue);
				} else if (newVector != null) {
					newVector.set(i, oldValue);
				}
			}
		}
		if (newVector != null) {
			newVector = vectorFactory.canonic(newVector);
		} else {
			newVector = vector;
		}
		cache.put(vector, newVector);
		return newVector;
	}

}