package eu.dnetlib.miscutils.collections;

import java.lang.reflect.InvocationTargetException;
import java.util.HashMap;
import java.util.Map;

import edu.emory.mathcs.backport.java.util.Arrays;

/**
 * Helper for creating a named key/value pairs out of a String.split output.
 * 
 * @author luca.santocono
 * 
 * @param <K>
 *            key type
 * @param <V>
 *            value type
 */
public class PositionalMapGenerator<K, V> {

	/**
	 * keys in positional order.
	 */
	private final K[] keys;

	/**
	 * positional keys declaration
	 * 
	 * @param keys
	 *            keys
	 */
	public PositionalMapGenerator(final K... keys) {
		this.keys = keys;
	}

	/**
	 * Positionally map the input array with the configured keys.
	 * 
	 * @param values
	 *            value array
	 * @return map containing value array mapped with keys
	 */
	public Map<K, V> asMap(final V[] values) {
		final Map<K, V> stringMap = new HashMap<K, V>();
		for (int i = 0; i < values.length; i++)
			stringMap.put(keys[i], values[i]);
		return stringMap;
	}

	@SuppressWarnings("unchecked")
	public <X, Y> X construct(final Class<X> clazz, final Class<Y> clavv, final V[] values) {
		Class<Y>[] params = new Class[values.length];
		Arrays.fill(params, clavv);

		try {
			return clazz.getDeclaredConstructor(params).newInstance(values);
		} catch (IllegalArgumentException e) {
			throw new IllegalStateException(e);
		} catch (InstantiationException e) {
			throw new IllegalStateException(e);
		} catch (IllegalAccessException e) {
			throw new IllegalStateException(e);
		} catch (InvocationTargetException e) {
			throw new IllegalStateException(e);
		} catch (SecurityException e) {
			throw new IllegalStateException(e);
		} catch (NoSuchMethodException e) {
			throw new IllegalStateException(e);
		}
	}

}
