Zapisywanie kilku danych w pliku

0

Siemano. Chciałbym zrobić coś a'la skarbonkę, a'la konto bankowe gdzie mógłbym zapisywać sobie stan mojego portfela, historię wydatków i tak dalej. I teraz pytanie. Czy jest opcja zapisania kilku zmiennych do pliku w taki sposób, że po jego wczytaniu mógłbym swobodnie je edytować?
Zrobiłem coś takiego:

public class Test {
public class Test {
    private Scanner scanner = new Scanner(System.in);
    
    public void dupa() throws FileNotFoundException {
            File file = new File("KontoBankowe.txt");
            Scanner in = new Scanner(file);
            String line = in.nextLine();
            System.out.println(line);
            int kwota = Integer.valueOf(line);
            kwota = kwota + scanner.nextInt();
            
            PrintWriter pw = new PrintWriter("KontoBankowe.txt");
            pw.printf(String.valueOf(kwota));
            pw.close();

        }
    }

    }

Ten fragment ma być odpowiedzialny za zmianę stanu konta. A co jeśli chciałbym do tego dodać także datę operacji i informację na co poszedł wydatek? Musiałbym tworzyć dwa kolejne pliki tekstowe?

0

Możesz w pliku stworzyć sobie strukturę w której każda linia mogła by zawierać kilka "kolumn" i każda kolumna zawierałaby zadane przez Ciebie wartości
Linia mogłaby wyglądac: NumerOperacji-Kwota-Data-Opis(myślniki w celu rozdzielnia kolumny). i wtedy w prosty sposób możesz sobie stworzyć interpreter do swoich potrzeb

0

Zapis obiektu do pliku: ObjectOutputStream
Odczyt obiektu z pliku: ObjectInputStream
Nie trzeba pisać parserów :)

0
    public void test() throws IOException {
        ObjectInputStream objectInputStream = new ObjectInputStream(new FileInputStream("costam.bin"));
        objectInputStream.read();
        int p = x.size();
        for(int i = 0; i<p; i++) {
            System.out.printf(x.get(i));
        }

        op.dzien = String.format("%tc", gregorianCalendar);
        op.kwota = scanner.nextInt();

        x.add(op.toString());
        ObjectOutputStream objectOutputStream = new ObjectOutputStream(new FileOutputStream("costam.bin"));
        objectOutputStream.writeObject(x);
        objectOutputStream.close();

        int z = x.size();
        for(int i = 0; i<z; i++){
            System.out.printf(x.get(i));
        }
    }
}

Hm. ObjectOutputStream i InputStream zachowują się jakby ich nie było. Gdzie leży błąd? :/

0

poważnie potrzebuję pomocy, nie mam pomysłu jak to rozwiązać. byłby ktoś miły?:D

1
  1. Dlaczego wpierw czytasz, a dopiero potem zapisujesz, i to do tego samego pliku, którego po odczycie nie zamknąłeś.
  2. Czytasz
objectInputStream.read();

ale nie zapamiętujesz tego co odczytałeś.
3. Jak wygląda obsługa błedów?

0

Nie wkleiłem całego kodu swoją drogą.

public class Test {
    private Scanner scanner = new Scanner(System.in);
    private Operacje op = new Operacje();
    private GregorianCalendar gregorianCalendar = new GregorianCalendar();
    private ArrayList<String> x = new ArrayList<String>();

    public void test() throws IOException {
        ObjectInputStream objectInputStream = new ObjectInputStream(new FileInputStream("costam.bin"));
        objectInputStream.read();
        int p = x.size();
        for(int i = 0; i<p; i++) {
            System.out.printf(x.get(i));
        }

        op.dzien = String.format("%tc", gregorianCalendar);
        op.kwota = scanner.nextInt();

        x.add(op.toString());
        ObjectOutputStream objectOutputStream = new ObjectOutputStream(new FileOutputStream("costam.bin"));
        objectOutputStream.writeObject(x);
        objectOutputStream.close();

        int z = x.size();
        for(int i = 0; i<z; i++){
            System.out.printf(x.get(i));
        }
    }
}
  1. Najpierw wczytuję bo już mam plik z danymi do odczytania.
  2. Hm. W jaki sposób mogę zapisać to co wczytałem by potem to wywołać?
  3. Na razie chcę poznać prawidłową konstrukcję wczytywania i zapisywania obiektów, potem dodam do tego błędy.
0

czas założyć konto, będąc gościem nie można edytować swoich wiadomości...
Tak jak napisałeś, że nie zamykam odczytu - dodałem linijkę objectInputStream.close();

1
  1. Skąd masz plik z danymi? Możesz go utworzyć wyłącznie korzystając z ObjectOutputStream.
  2. Czytanie powinno wyglądać tak:
NazwaKlasy dane = (NazwaKlasy)objectInputStream.readObject();

NazwaKlasy zależy od tego jaki obiekt zapisałeś do pliku.
3. Błędy (wyjątki) musisz obsłużyć w pierwszej kolejności - w ten sposób się dowiesz co poszło źle.

0

Na początku rozpocząłem od napisania samego ObjectOutputStream, żeby zacząć to pojmować. W ten sposób utworzyłem sobie plik z tablica. Usunąłem go, rozbiłem sobie "program" na dwie klasy.

public class Odczyt {

    public void test() throws IOException, ClassNotFoundException {
         Zapis test2 = new Zapis();
        test2.test();
        ObjectInputStream objectInputStream = new ObjectInputStream(new FileInputStream("costam.bin"));
        objectInputStream.read();
        Zapis test = (Zapis)objectInputStream.readObject();
        System.out.println(test);
        }
    }
public class Zapis {
    private Operacje op = new Operacje();
    private GregorianCalendar gregorianCalendar = new GregorianCalendar();
    private Scanner scanner = new Scanner(System.in);
    private ArrayList<String> x = new ArrayList<String>();

    public void test() throws IOException {
        op.dzien = String.format("%tc", gregorianCalendar);
        op.kwota = scanner.nextInt();

        x.add(op.toString());
        ObjectOutputStream objectOutputStream = new ObjectOutputStream(new FileOutputStream("costam.bin"));
        objectOutputStream.writeObject(x);
        objectOutputStream.close();

        int z = x.size();
        for (int i = 0; i < z; i++) {
            System.out.printf(x.get(i));
        }
    }
}

Wyskakuje mi błąd w Odczycie

     Zapis test = (Zapis)objectInputStream.readObject();

Exception in thread "main" java.lang.ClassCastException: java.util.ArrayList cannot be cast to Zapis.
Hm.

2

Myśl, musisz zapisywać i odczytywać obiekt tego samego typu. Skoro zapisujesz tak:

ArrayListString> x =...;
objectOutputStream.writeObject(x);

to odczyt musi wyglądać tak:

ObjectInputStream objectInputStream = new ObjectInputStream(new FileInputStream("costam.bin"));
//objectInputStream.read(); usuń ten wiersz!
ArrayList<String> test = (ArrayList<String>)objectInputStream.readObject();
0

Dzięki wielkie Bogdan! Wszystko już działa poprawnie. Teraz to tylko sensownie poukładać w ładny kod i będzie miodzio. Bez Ciebie by mi się nie udało. Ogromne wyrazy wdzięczności! :) Działający kod wygląda następująco:

public class Odczyt {

    public static ArrayList<String> array;

    public void test() throws IOException, ClassNotFoundException {
        Zapis test2 = new Zapis();
        ObjectInputStream objectInputStream = new ObjectInputStream(new FileInputStream("costam.bin"));
        array = (ArrayList) objectInputStream.readObject();
        int k = array.size();
        for (int i = 0; i < k; i++) {
            System.out.println(array.get(i));
        }
        test2.test();
    }
}
 
public class Zapis {
    private Operacje op = new Operacje();
    private GregorianCalendar gregorianCalendar = new GregorianCalendar();
    private Scanner scanner = new Scanner(System.in);
    private ArrayList<String> x = new ArrayList<String>();
    private Odczyt odczyt;

    public void test() throws IOException {
        op.dzien = String.format("%tc", gregorianCalendar);
        op.kwota = scanner.nextInt();
        int g = odczyt.array.size(); // pomocnicze
        for (int i = 0; i < g; i++) {
            x.add("");
            x.set(i, odczyt.array.get(i));
        }

        x.add(op.toString());
        ObjectOutputStream objectOutputStream = new ObjectOutputStream(new FileOutputStream("costam.bin"));
        objectOutputStream.writeObject(x);
        objectOutputStream.close();

    }
}
0

Ba! Nie udało by się bez błędów podczas porządkowania.

class Zapis {
    private Operacje op = new Operacje();
    private GregorianCalendar gregorianCalendar = new GregorianCalendar();
    private Scanner scanner = new Scanner(System.in);
    private ArrayList<String> x = new ArrayList<String>();
    private Odczyt historia;

    public void test() throws IOException, ClassNotFoundException, NullPointerException {
        try {
        op.dzien = String.format("%tc", gregorianCalendar);
        op.kwota = scanner.nextInt();
        scanner.nextLine();
        op.naco = scanner.nextLine();
        int tablesize;
       tablesize = historia.array.size();
        for (int i = 0; i < tablesize; i++) {
            x.add("");
            x.set(i, historia.array.get(i));
        }
            x.add(toString());
        ObjectOutputStream objectOutputStream = new ObjectOutputStream(new FileOutputStream("costam.bin"));
        objectOutputStream.writeObject(x);
        objectOutputStream.close();
        ;
        }catch (NullPointerException e){
            ObjectOutputStream objectOutputStream = new ObjectOutputStream(new FileOutputStream("costam.bin"));
            op.dzien = String.format("%tc", gregorianCalendar);
            op.kwota = scanner.nextInt();
            x.add(op.toString());
            objectOutputStream.writeObject(x);
            objectOutputStream.close();
public class Odczyt {

    public static ArrayList<String> array;

    public void test() throws IOException, ClassNotFoundException {
        Zapis test2 = new Zapis();
        ObjectInputStream objectInputStream = new ObjectInputStream(new FileInputStream("costam.bin"));
        array = (ArrayList) objectInputStream.readObject();
        int k = array.size();
        for (int i = 0; i < k; i++) {
            System.out.println(array.get(i));
        }
        test2.test();
    }
}

Przy przypisywaniu wartości dla tablesize wyskakuje NullPointerException.
Debugger pokazuje:
user image

0

Błędy są oczywiste, po tym:

private Odczyt historia;

zmienna historia ma wartość null, zamień na:

private Odczyt historia = new Odczyt();

wtedy dla odmiany zmienna historia.array będzie nullem, możesz to poprawić wywołując

historia.test();

Wskazane poprawki to, IMHO, tzw. pudrowanie gówna. Ten kod ma niewielki sens, dlaczego klasa Zapis zaczyna od próby odczytu?

0

Klasa zapis w moim mniemaniu miała:

  • ustawić kwotę i dzień w którym wprowadzono dane.
  • wstawić ustawione dane do tablicy
    • w tym celu pętlą pobieram każdy element tablicy z istniejącego już pliku i dodaje do nich kolejny index.
  • zapisać obiekt tablicy do pliku w celu późniejszego odczytania.
0

Co do poprzedniego bledu to pomogło mi dopisanie

 new ArrayList<String>; 

W klasie odczytu

1 użytkowników online, w tym zalogowanych: 0, gości: 1