/* Programmname: Verwalten einer Datei
* Datenhaltungs-Klasse: Direktzugriffsspeicher
* Aufgabe: Lesen und Schreiben von Sätzen fester Länge
* in einen Direktzugriffsspeicher
*/

import java.io.*;

public class Datei
{
    private RandomAccessFile eineStammdatei;
	private int Aktuell; //aktuelle Position des Dateizeigers
	private final int SATZLAENGE = 100;
    private String Dateiname = "Stammdatei.txt"; // Dateiname
	//Konstruktor
    public Datei()
    {
        oeffneDatei(Dateiname);
	}
    //Operationen
    public void speichereSatz(String Satz, int index) throws IOException
	{
	    //Speichert einen Datensatz Satz an einer Position index in der Datei
	    if(eineStammdatei != null)
        {
            positioniereAufSatz(index); //interne Hilfsoperation
            writeFixedString(Satz, SATZLAENGE); //interne Hilfsoperation
        }
	}
	public String leseSatz(int index)throws IOException
	{
	    //Liest den Datensatz index aus der Datei und gibt ihn als String zurück
        if(eineStammdatei != null)
        {
            positioniereAufSatz(index); //interne Hilfsoperation
            return readFixedString(SATZLAENGE); //interne Hilfsoperation
        }
        else return null;
	}

	public void oeffneDatei(String name)
	{
	    //Öffnen der Datei zum Lesen und Schreiben
        try
        {
            eineStammdatei = new RandomAccessFile(name, "rw");
        }
        catch (IOException e)
        {
            //Testausgabe
            System.out.println("Datei:oeffneDatei: " + e);
        }
    }
    public void schliesseDatei()
    {
	    // Schließen der Datei
        try
        {
            eineStammdatei.close();
        }
        catch (java.io.IOException e)
        {
            //Testausgabe
            System.out.println("Datei:schliesseDatei: " + e);  
        }
    }
    public int gibAnzahlDatensaetze()
    {
        // Rückgabe der Dateilänge in Datensätzen (!)
        long Anzahl=0;
        try 
        {
            Anzahl=eineStammdatei.length();
        } 
        catch (IOException e)
        {
            //Testausgabe
            System.out.println("Datei:gibAnzahlDatensaetze: " + e);    
        }
        return (int)(Anzahl / (long)(SATZLAENGE * 2));//Umrechnung auf Anzahl Datensätze
    }
    //Hilfsoperationen
    private void positioniereAufSatz(int index)throws IOException
    {
        // Positioniert in der Datei auf den Datensatz mit der Position index
        if(eineStammdatei != null)
        {
            try
            {
                eineStammdatei.seek(index * SATZLAENGE * 2);
            }
            catch(IOException e)
            {
                //Testausgabe
                System.out.println("Datei:positioniereAufSatz: " + e); 
            }
        }
    }
    private String readFixedString(int Laenge)throws IOException
    {
        // Liest einen String der festen Länge Laenge (Unicode = 1 Zeichen = 2 Byte) ein
        StringBuffer einPuffer = new StringBuffer(Laenge);
        int i = 0;
        while(i < Laenge)
        {
            char Zeichen = eineStammdatei.readChar();
            i++;
            if(Zeichen == 0) //Ende der Nutzdaten
            {
                //eineStammdatei.skipBytes(2*(Laenge-i));//Rest mit 0 überlesen
                //wird benötigt, wenn hinter dem String z.B. noch Zahlen kommen
                return einPuffer.toString();
            }
            else einPuffer.append(Zeichen);//Anhängen an den Puffer
        }
        return einPuffer.toString();
    }
    private void writeFixedString(String einDatensatz, int Laenge) throws IOException
    {
        // Schreibt einen String einDatensatz der festen Länge Laenge weg
        for(int i = 0; i < Laenge; i++)
        {
            char Zeichen = 0;
            if(i < einDatensatz.length()) 
                Zeichen = einDatensatz.charAt(i); //liefert das Zeichen an der i-ten Stelle
            //Der Rest wird mit 0 aufgefüllt
            eineStammdatei.writeChar(Zeichen); //zeichenweises Schreiben in die Stammdatei
        }
    }
}
