/*
 * File: CurrencyConversionTable.java
 * ----------------------------------
 * This file provides a general abstraction for reading currency
 * conversion rates from a data file.
 */

import acm.util.*;
import java.io.*;
import java.util.*;

/**
 * This class exports methods for converting from one currency to
 * another based on data from a file.
 */

public class CurrencyConversionTable {

/**
 * Constructs a new CurrencyConversionTable from the data in the
 * specified file.  The table consists of lines in the following form:
 *
 *   code rate name
 *
 * where currency is the name of the currency, rate is a floating-point
 * value specifying the equivalent value of one unit of that currency
 * in the standard currency (typically USD, even though that is not
 * required), and the full name of the currency as it appears on
 * oanda.com.  This method throws an ErrorException if the file
 * cannot be found or contains data errors.
 */
	public CurrencyConversionTable(String filename) {
		try {
			BufferedReader rd = new BufferedReader(new FileReader(filename));
			rateTable = new TreeMap<String,CurrencyEntry>();
			while (true) {
				String line = rd.readLine();
				if (line == null) break;
				int sp1 = line.indexOf(' ');
				int sp2 = line.indexOf(' ', sp1 + 1);
				if (sp1 != 3 || sp2 == -1) {
					throw new ErrorException("Illegal exchange rate line");
				}
				String code = line.substring(0, sp1);
				double rate = Double.parseDouble(line.substring(sp1 + 1, sp2));
				String name = line.substring(sp2 + 1);
				rateTable.put(code.toUpperCase(), new CurrencyEntry(code, name, rate));
			}
			rd.close();
		} catch (IOException ex) {
			throw new ErrorException(ex);
		} catch (NumberFormatException ex) {
			throw new ErrorException("Illegal number in data file");
		}
	}

/**
 * Returns an array of the currency codes in alphabetical order.
 * 
 * @return An array of the currency codes in alphabetical order
 */
	public String[] getCurrencyCodes() {
		Set<String> currencies = rateTable.keySet();
		return currencies.toArray(new String[currencies.size()]);
	}

/**
 * Returns the full name for the specified currency code.  If the
 * code does not exist, this method throws an ErrorException.
 * 
 * @return The full name for the currency code
 */
	public String getName(String code) {
		CurrencyEntry entry = rateTable.get(code.toUpperCase());
		if (entry == null) {
			throw new ErrorException("No currency for " + code);
		}
		return entry.getName();
	}

/**
 * Returns the current rate for the specified currency code.  If
 * the code does not exist, this method throws an ErrorException.
 * 
 * @return The current exchange rate for the specified code
 */
	public double getRate(String code) {
		CurrencyEntry entry = rateTable.get(code.toUpperCase());
		if (entry == null) {
			throw new ErrorException("No entry for " + code);
		}
		return entry.getRate();
	}

/* Instance variables */
	private TreeMap<String,CurrencyEntry> rateTable;

}
