import york.YorkReader;

/**
 * Prints the first n Fibonacci numbers, where n is provided as a command 
 * line argument.  If n is smaller than 1, the first Fibonacci number is
 * printed.
 *
 * Recovers when the user provides a command line argument which cannot
 * be interpreted as an integer.
 *
 * @version     1.1    May 29, 2001
 * @author      Franck van Breugel
 */
public class ImprovedFibonacci 
{
    /**
     * Prints the first n Fibonacci numbers.
     *
     * @param n The number of Fibonacci numbers to be printed.
     */
    public static void fibonacci(int n) 
    {
        int lo = 1; // f(0)
        int hi = 1; // f(1)
        System.out.println(lo);
        for (int i = 1; i < n; i++) 
        { 
            /* lo = f(i-1) and hi = f(i) */
            System.out.println(hi);
            int temp = hi;
            hi = lo + hi;
            lo = temp; 
        }
    }

    /**
     * Interprets the specified string as an integer.
     * If the specified string cannot be interpreted as an integer,
     * the user is asked to provide an integer.
     *
     * @param s String.
     */
    public static int parse(String s)
    {
        boolean invalid = true;
        int n = 0;
        while (invalid)
	{
            try
	    {
                n = Integer.parseInt(s);
                invalid = false; // not executed if the above method call throws an exception
            }
            catch (NumberFormatException e)
	    {
                System.out.print("Please provide an integer: ");
                YorkReader reader = new YorkReader("System.in");
                s = reader.readWord();
	    }
        }
        return n;
    }

    /**
     * Prints the first n Fibonacci numbers, where n is provided as a 
     * command line argument. 
     */
    public static void main(String[] args) 
    {
	fibonacci(parse(args[0]));
    } 
}
