C++

Odczyt i zapis danych z pliku w C++, Java i Python

Nie kojarzę żadnego maturalnego zadania, na którym nie wymagano by stworzenia programu pracującego na danych z pliku tekstowego. Jeśli nie potrafisz tego zrobić to nie łudź się, że zdobędziesz jakiekolwiek punkty z zadania na program. W tym wpisie pokażę jak zrobić odczyt i zapis danych z pliku w językach C++, Java oraz Python.

Odczyt danych z pliku tekstowego

W celu odczytania danych z pliku tekstowego posługiwać będziemy się obiektami klasy fstream w języku C++. W Javie posłużymy się obiektem typu BufferedReader, a Pythonie użyjemy wbudowanej funkcji open. Zakres wiedzy wymaganej na maturze z informatyki nie zahacza właściwie o programowanie obiektowe, więc dla uproszczenia powiedzmy sobie, że będziemy używać zmiennych plikowych i przypisanych im funkcji.

Otwieranie pliku - C++ i Python

W pierwszej kolejności tworzymy zmienną plikową, postępując analogicznie do deklarowania zmiennej liczbowej czy tekstowej.Następnie musimy otworzyć plik, aby mieć do niego jakikolwiek dostęp. W C++ i Python użyjemy metody open (w C++ jest ona wbudowana w zmienną plikową, zaś w Pythonie jest ona dostępna globalnie). Metody te przyjmują dwa argumenty. Pierwszym jest nazwa pliku wraz z rozszerzeniem .txt podana jako łańcuch znaków, a drugim tryb otwarcia pliku. W tym przypadku jest to tryb input (ang. wejście - w sensie do pliku źródłowego) w postaci ios::in w C++ oraz "r" w Pythonie. W języku C++ niezbędne jest dodanie do pliku biblioteki fstream za pomocą dyrektywy preprocesora #include <fstream>.

fstream plik;//tworzymy zmienną plikową plik.open("nazwa.txt", ios::in);//używamy metody open
file = open("nazwa.txt", "r") #tworzymy zmienną plikową przy uzyciu methody open

Otwieranie pliku - Java

Nieco inaczej sytuacja wygląda w języku Java. Tutaj najpierw deklarujemy zmienną plikową za pomocą new File("ścieżkadopliku.txt"). Następnie wypada sprawdzić, czy podany plik w ogóle istnieje. Jeżeli wszystko jest OK, to tworzymy zmienną typu BufferedReader. Tworząc ją korzystamy również z obiektu FileReader, w którym wskażemy plik.

File f = new File("nazwa.txt"); //tworzymy zmienną plikową - używamy tutaj obiektu File z java.io
		if(!f.exists()) //przed rozpoczęciem jakichkolwiek prac z plikiem warto sprawdzić, czy w ogóle istnieje
		{
			System.out.println("Plik " + f.getName() + " nie został odnaleziony."); //jeżeli nie, to zakańczamy pracę programu
			return;
		}
		BufferedReader br = new BufferedReader(new FileReader(f)); // do odczytu plików tworzymy nowa instancję BufferedReader 

Otworzyliśmy plik - co dalej?

Następnie należy sprawdzić, czy w ogóle udało się otworzyć plik. Jest kilka możliwości. Metod sprawdzania poprawności otworzenia pliku jest kilka, ale ja nie będę się rozdrabniał i pokażę wam czego sam używam:

C++

if(!plik) { cout << "Uuuu kiepściutko. Nie udało się. return 1; //do zasygnalizowania, że coś poszło nie tak i zakończenia programu }else { //dalsza część programu } 

Java

if(br.ready()) { //jeżeli BufferedReader jest gotowy do odczytu, to oznacza, że możemy przystąpić do pracy z plikiem
			//dalsza część programu
		}
		else
		{
			System.out.println("Karamba, coś poszło nie tak."); //jeżeli nie, to zakańczamy pracę programu
			br.close(); //zwalniamy zasoby
			return;
		}

Python

if file.closed: #jezeli plik od razu jest zamkniety
    print("Plik " + file.name + " nie moze zostac otworzony.") #to oznacza ze cos poszlo nei tak
#dalszy program

Czytanie zawartości pliku

C++

Z pliku tekstowego w C++ zazwyczaj czytamy w ten sposób, że pobieramy każdą kolejną wartość oddzieloną białymi znakami. To znaczy, że nieważne, czy wartości będą oddzielone enterem, tabulatorem, kilkoma spacjami i tak odczytana zostanie ta wartość po białych znakach. No dobra ale jak to zrobić? Otóż wystarczy stworzyć zmienną typu string, int itd (w zależności od potrzeb) i zadziałać tak samo jak przy obiekcie cin, tzn.:

plik >> zmienna;

Program pobierze z pliku daną wartość i zapisze ją do naszej zmiennej.

Java i Python

W języku Java i Python czytamy cały wiersz do zmiennej. W obu przypadkach wiersz zostanie wczytany jako zmienna tekstowa. Jeżeli chcemy więc odczytać liczby z pliku, to musimy najpierw je odpowiednio przekonwertować.

String line = br.readLine(); //czytanie pojedynczego wiersza do zmiennej w Javie 
line = file.read() #czytanie pojedynczego wiersza do zmiennej w Pythonie

Wczytywanie w pętli

Jeżeli do odczytania mamy więcej niż jedną daną to możemy użyć pętli. Najwygodniejsza będzie pętla while w Javie i C++ oraz pętla for w Pythonie.

while(plik >> zmienna) { 
//Rób coś
}
String line;
while((line = br.readLine()) != null) { //dopóki za zmienną line nie zostanie przypisana wartość null wykonuj kod
			//zrób coś z wierszem
		}
for wiersz in file: #petla for iterujaca poprzez wszystkie wiersze w pliku
    print(wiersz) #uwaga: wiersz zazwyczaj zakonczony jest symbolem \n - trzeba to zawsze uwzglednic
    #rob cos dalej z wierszem...

W tym przypadku program będzie wypisywał każdą kolejną daną z pliku, aż do jego końca.

grupa wsparcia matura z informatyki

Zapis danych do pliku

C++ i Python

Na początku postępujemy podobnie jak to miało miejsce w przypadku odczytu danych z pliku. Tworzymy zmienną plikową i korzystamy z open(). Jednakże tym razem zamiast trybu input użyjemy trybu output (ang. wyjście, w sensie z pliku źródłowego).

fstream plik;//tworzymy zmienną plikową 
plik.open("nazwa.txt", ios::out);//używamy metody open
file = open("nazwa.txt", "w") #otwieramy plik nazwa.txt w trybie zapisywania - jezeli plik nie istnieje utworzy go #jezeli zas plik istnieje - zostanie nadpisany

W C++ zapisujemy do pliku tak samo, jak to robimy w przypadku wypisywania w konsoli. Z tą malutką różnicą, że zamiast cout wpisujemy nazwę zmiennej plikowej. W Pythonie posłużymy się metodą write().

plik << 45.77; plik << " " << nazwa_jakiejs_zmiennej << "\t" << "tekst" << endl; plik << "\n\n\n\n"; plik << 9+11;
file.write("Coś, co wpisze do pliku \n") #wpisujemy wiersz do pliku, symbol \n oznacza nowy wiersz 

Java

W przypadku Javy również tworzymy zmienną typu File. Następnie jednak korzystamy z obiektu BufferedWriter. Inicjalizujemy go za pomocą obiektu FileWriter, który wskazuje plik.

File f1 = new File("nazwa.txt"); //tworzymy zmienną plikową - używamy tutaj obiektu File z java.io
		if(!f1.exists()) //przed rozpoczęciem jakichkolwiek prac z plikiem warto sprawdzić, czy w ogóle istnieje
		{
			System.out.println("Plik " + f1.getName() + " nie został odnaleziony."); //jeżeli nie, to zakańczamy pracę programu
			return;
		}
		BufferedWriter bw = new BufferedWriter(new FileWriter(f1)); // do zapisu do pliku używamy instancji obiektu BufferedWriter

Następnie, podobnie jak w Pythonie, korzystamy z metody write():

bw.write("Coś, co wpiszę do pliku"); // w ten sposób zapisujemy tekst do pliku(uwaga - dopóki nie przejdziemy do następnego wiersza, BufferedWriter będzie zapisywał wszystko w jednej linii)
		bw.newLine(); // jeżeli chcemy przejść do nowego wiersza używamy metody newLine() - można również to osiągnąć dodając \n w String

Zamykanie pliku

Zarówno w przypadku odczytywania danych, jak i zapisywania należy pamiętać o zamknięciu pliku, jeżeli nie mamy w nim nic więcej do roboty. Dzięki temu ustrzeżemy się problemów. Plik zamykamy w następujący sposób:

plik.close();
bw.close();// w obu przypadkach musimy pamiętać, aby zamknąć plik
		br.close();// w celu zwolnienia zasobów
file.close() #zawsze trzeba zamknac plik, gdy przestanie nam on być potrzebny

Odczyt i zapis danych z pliku C++, Java, Python

Pozwoliłem stworzyć sobie krótkie zadanie, na którym przedstawię całą wiedzę zawartą powyżej. Mamy stworzyć programy, które wypiszą zarobki pana Z w poszczególnych miesiącach podane w pliku zarobki.txt oraz zsumuje je i zapisze w nowym pliku.

Tutaj macie link z danymi i kodem źródłowym.

C++

#include <iostream>
#include <fstream>

using namespace std;

int main()
{
	
	cout << "Tak wygladaja zarobki pana Z z ubieglego roku:" << endl;
	
	fstream plik;
	plik.open("zarobki.txt", ios::in);
	
	if(!plik)
	{
		cout << "Dupa blada. Nie udalo sie utworzyc pliku.";
		return 1;
	}else
	{
		string miesiac;
		float pensja, suma=0;
		
		
		while(plik >> miesiac >> pensja)
		{
			cout << miesiac << " - " << pensja << endl;
			suma+=pensja;
		}
		
		cout << "Przez caly rok Pan Z zarobil: " << suma << endl;
		
		plik.close();
	
		plik.open("suma.txt", ios_base::out);
		
		if(!plik)
		{
		cout << "Dupa blada. Nie udalo się utworzyc pliku.";
		return 1;
		}else
		{
		plik << suma;
		plik.close();
		}

		
	}
	
	
	return 0;
}

Java

package matura;

import java.io.IOException;
import java.io.Writer;
import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.Reader;
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.File;

public class Main
{
    public static void main(final String[] args) throws IOException {
        File f = new File("zarobki.txt");
        if (!f.exists()) {
            System.out.println("Plik " + f.getName() + " nie został odnaleziony.");
            return;
        }
        final BufferedReader br = new BufferedReader(new FileReader(f));
        if (!br.ready()) {
            System.out.println("Ajajaj, coś poszło nie tak.");
            br.close();
            return;
        }
        float suma = 0.0f;
        float pensja = 0.0f;
        String line;
        while ((line = br.readLine()) != null) {
            final String[] splitted = line.split(" ");
            final String miesiac = splitted[0];
            pensja = Float.parseFloat(splitted[1]);
            System.out.println(String.valueOf(miesiac) + " - " + pensja);
            suma += pensja;
        }
        System.out.println("Przez cały rok Pan Z zarobił " + suma);
        br.close();
        f = new File("suma.txt");
        if (!f.exists()) {
            System.out.println("Plik " + f.getName() + " nie został odnaleziony.");
            return;
        }
        final BufferedWriter bw = new BufferedWriter(new FileWriter(f));
        bw.write("Suma zarobków: " + suma);
        bw.close();
    }
}

Python

file = open("zarobki.txt", "r")
suma = 0.0
pensja = 0.0
for line in file:
    splitted = line.split(" ")
    miesiac = splitted[0]
    pensja = float(splitted[1])
    print(miesiac + " - " + str(pensja))
    suma += pensja
print("Przez cały rok Pan Z zarobił " + str(suma))
file.close()
file = open("suma.txt", "w")
file.write("Suma zarobków: " + str(suma))
file.close()
Dyskusja archiwalna

Komentarze (1)

Komentarze pochodzą z poprzedniej wersji bloga i pozostają tylko do odczytu.

  1. Clay

    Jakby wyglądał kod jeśli chcielibyśmy wyświetlić zarobki z konkretnego miesiąca