/*
 * LVfileIO.java
 *
 * Created on August 9, 2004, 7:22 PM
 */

package LotkaVolterra;

import java.io.*;
import java.util.StringTokenizer;

public final class LVfileIO {
    
    
    /** Creates a new instance of LVfileIO */
    private LVfileIO() {}
    
    
    public static void saveAnimalsintoFile(Animal[] animal, String filename, String commentLine) {
        
        
        try {
            
            PrintWriter fileOut = new PrintWriter(new FileWriter(new File(filename)));
            String temp;

            // Write line 1, the comment line
            fileOut.println(commentLine);

            // Write line 2, numberOfSpecies
            fileOut.println(animal.length + " 800 0.01");

            // Write line 3, growth rates
            temp = "";
            for (int i = 0; i < animal.length; i++) {
                temp = temp + animal[i].r + " ";
            }
            fileOut.println(temp);

            // Write line 4, initial populations
            temp = "";
            for (int i = 0; i < animal.length; i++) {
                temp = temp + animal[i].getX() + " ";
            }
            fileOut.println(temp);

            // Write line 5, colors
            temp = "";
            for (int i = 0; i < animal.length; i++) {
                temp = temp + 0 + " ";
            }
            fileOut.println(temp);        
            // nobody cares about colors.

            // Wrtie Line 6 through line (6 + numberOfSpecies)
            double[][] alphaMatrix = LVmatrix.createAlphaMatrix(animal);
            
            for (int i = 0; i < animal.length; i++) {
                
                temp = "";
                for (int j = 0; j < animal.length; j++) {
                    temp = temp + alphaMatrix[i][j] + " ";
                }
                
               fileOut.println(temp);
            } // end if i loop
            
            fileOut.close();
            
        } catch (Exception e) {
            System.out.println("Error writing File!");
        }
        
    }  // End of saveAnimalsToFile
    
    
    public static Animal[] createAnimalsFromFile(String paramFile) {
        
        Animal[] animalsFromFile = new Animal[0];
        
        try {
            
            if ((paramFile.toLowerCase()).endsWith("dat")) {
                animalsFromFile = readFromSprottStyle(paramFile);
            } else {
                animalsFromFile = readFromJMStyle(paramFile);
            }
                
        } catch (FileNotFoundException fnfe) {
            System.out.println("File " + paramFile + " not found!");
        } catch (IOException ioe) {
            System.out.println("Some IO exception occured.");
        }  catch (NumberFormatException nfe) {
            System.out.println("File " + paramFile + " not formatted correctly!");
        } // end of try/catch
        
        return animalsFromFile;
    }  // End of initializeAnimalsWithFile method
    
    
    public static Animal[] readFromJMStyle(String paramFile) throws FileNotFoundException, IOException, NumberFormatException {
        
        // These four piece of data will
        // be extrated from the file
        int numberOfSpecies;
        double[] growthRate;
        double[] initialPopulation;
        double[][] alphaMatrix;
        
        
        BufferedReader fileIn = new BufferedReader(new FileReader(new File(paramFile)));
        StringTokenizer nextLine;
            
        // Read line 1, the comment line
        nextLine = new StringTokenizer(fileIn.readLine(), " ");
            
        // Read line 2, numberOfSpecies
        nextLine = new StringTokenizer(fileIn.readLine(), " ");
        numberOfSpecies = Integer.parseInt(nextLine.nextToken());            
            
        // Read line 3, growth rates
        growthRate = new double[numberOfSpecies];
        nextLine = new StringTokenizer(fileIn.readLine(), " ");
            
        for (int i = 0; i < numberOfSpecies; i++) {
            growthRate[i] = Double.parseDouble(nextLine.nextToken());
        }
            
        // Read line 4, initial populations
        initialPopulation = new double[numberOfSpecies];
        nextLine = new StringTokenizer(fileIn.readLine(), " ");
           
        for (int i = 0; i < numberOfSpecies; i++) {
            initialPopulation[i] = Double.parseDouble(nextLine.nextToken());
        }
            
        // Read line 5, colors
        nextLine = new StringTokenizer(fileIn.readLine(), " ");
        // nobody cares about colors.
           
        // Read Line 6 through line (6 + numberOfSpecies)
        alphaMatrix = new double[numberOfSpecies][numberOfSpecies];
        int i = 0;
            
        while (fileIn.ready() && i < numberOfSpecies) {
            nextLine = new StringTokenizer(fileIn.readLine(), " ");
                
            for (int j = 0; j < numberOfSpecies; j++) {
                alphaMatrix[i][j] = Double.parseDouble(nextLine.nextToken());
            }
                
            i++;
        }
            
            
        // Now with the parameters extracted we can create an Animal array
        Animal[] animalsFromFile = new Animal[numberOfSpecies];
            
        for (int j = 0; j < numberOfSpecies; j++) {
            animalsFromFile[j] = new Animal(growthRate[j], initialPopulation[j], alphaMatrix[j]);
        }
        
        fileIn.close();
        return animalsFromFile;
    }  // End of the readFromJMStyle method
    
    
    public static Animal[] readFromSprottStyle(String paramFile) throws FileNotFoundException, IOException, NumberFormatException {
        
        // These four piece of data will
        // be extrated from the file
        int numberOfSpecies;
        double[] growthRate;
        double[] initialPopulation;
        double[][] alphaMatrix;
        
        BufferedReader fileIn = new BufferedReader(new FileReader(new File(paramFile)));
        StringTokenizer line;
        
        // Read line 1, Random Number Generator Seed
        line = new StringTokenizer(fileIn.readLine());
        
        // Read line 2, Number of Species
        line = new StringTokenizer(fileIn.readLine());
        numberOfSpecies = Integer.parseInt(line.nextToken());
        
        // Read line 3 through (3 + N), Initial Populations
        initialPopulation = new double[numberOfSpecies];
        for (int i = 0; i < numberOfSpecies; i++) {
            line = new StringTokenizer(fileIn.readLine());
            initialPopulation[i] = Double.parseDouble(line.nextToken());
        }
        
	// Read the next N lines to be Growth Rates
        growthRate = new double[numberOfSpecies];
        for (int i = 0; i < numberOfSpecies; i++) {
            line = new StringTokenizer(fileIn.readLine());
            growthRate[i] = Double.parseDouble(line.nextToken());
        }
        
        // Read the next N*N lines to be the competition Matrix
        alphaMatrix = new double[numberOfSpecies][numberOfSpecies];
        for (int i = 0; i < numberOfSpecies; i++) {
            for (int j = 0; j < numberOfSpecies; j++) {
                line = new StringTokenizer(fileIn.readLine());
                alphaMatrix[i][j] = Double.parseDouble(line.nextToken());
            }
        }
        
        // Now with the parameters extracted we can create an Animal array
        Animal[] animalsFromFile = new Animal[numberOfSpecies];
            
        for (int j = 0; j < numberOfSpecies; j++) {
            animalsFromFile[j] = new Animal(growthRate[j], initialPopulation[j], alphaMatrix[j]);
        }
        
        fileIn.close();
        return animalsFromFile;
    }  // End of the readFromSprottStyle method
    
    
    // Write text into a new file
    // useful for writing data
    public static void writeIntoNewFile(String text, String filename) {

        try {
            
            PrintWriter fileOut = new PrintWriter(new FileWriter(new File(filename)));
            
            fileOut.println(text);
            
            fileOut.close();
            
        } catch (Exception e) {
            System.out.println("Error writing File!");
        }
    } // End of writeTextIntoFile

    
    // Append text into a new file
    // useful for writing data
    public static void writeIntoExistingFile(String text, String filename) {

        try {
            // this will append text
            PrintWriter fileOut = new PrintWriter(new FileWriter(filename, true));
            
            fileOut.println("\n" + text);
            
            fileOut.close();
            
        } catch (Exception e) {
            System.out.println("Error writing File!");
        }
    } // End of writeTextIntoFile
}  // End of the LVfileIO class