Operacje wejścia - wyjścia
Podziały systemów wejścia - wyjścia:
1) ze względu na poziom realizacji
1.1. standardowe wejście - wyjście - ukryte buforowanie danych
1.1.1. Znakowe
1.1.2. Łańcuchowe
1.1.3. Formatowane
1.1.4. Rekordowe
1.2. systemowe wejście - wyjście - jawne buforowanie danych w programie
2) ze względu na sposób zapisu danych do pliku
2.1. format znakowy - konwersja na postać znakową danych
2.2. format binarny - brak konwersji na postać znakową
3) ze względu styl programowania
3.1. proceduralne - zbiór funkcji realizujących operacje wejścia i wyjścia
3.2. obiektowe - zbiór klas reprezentujących urządzenia wejściowe i wyjściowe
Podział urządzeń przetwarzanych za pomocą operacji wejścia - wyjścia
· konsola (monitor i klawiatura), drukarka,
· pliki dyskowe
Sposób przetwarzania urządzeń fizycznych za pomocą operacji wejścia - wyjścia:
· otwarcie plików dyskowych oraz kontrola poprawności otwarcia (pozostałe urządzenia są zawsze otwarte)
· czytanie, pisanie wraz z kontrolą poprawności tych operacji
· zamknięcie plików dyskowych
1 Standardowe wejście - wyjście
· urządzenia fizyczne są reprezentowane w programach przez strumienie typu FILE (struktura zdefiniowana w pliku stdio.h)
· predefiniowane nazwy strumieni zw. standardowymi strumieniami wejścia - wyjścia związane ze standardowymi fizycznymi urządzeniami wejścia - wyjścia
Nazwa strumienia
Zastosowanie strumienia
stdin
strumień wejściowy (normalnie klawiatura)
stdout
strumień wyjściowy (normalnie ekran)
stderr
strumień komunikatów błędów (zawsze ekran)
stdaux
strumień pomocniczy (np. port szeregowy)
stdprn
strumień drukarki
· otwieranie plików:
deklaracja w stdio.h:
FILE *fopen(const char *filename, const char *mode); gdzie:
* funkcja zwraca NULL w przypadku nieudanego otwarcia pliku, w przeciwnym wypadku wskaźnik na strukturę reprezentującą strumień
* filename (łańcuch zawierający nazwę pliku dyskowego lub nazwę urządzenia standardowego („PRN”, „CON”,”COM”)
* mode (łańcuch opisujący tryb pracy):
Łańcuch
Opis trybu otwarcia
r
tylko do czytania istniejącego pliku
w
do zapisu - w utworzonym pliku lub w istniejącym pliku, niszcząc jego zawartość
a
do dopisywania - pisanie na końcu istniejącego pliku lub pisanie w utworzonym pliku
+
do zapisu i odczytu; w+ przy zapisie niszczy zawartość istniejącego pliku
t
w trybie tekstowym (konwersja znakowa)
b
w trybie binarnym (bez konwersji znakowej)
np.: „w”, „w+”, „w+b” lub „wb+”
Uwagi:
Þ jeśli nie oznacza się „t” lub „b”, to plik jest otwierany domyślnie w trybie tekstowym, jeśli _fmode == O_TEXT lub binarnym jeśli _fmode == O_BINARY (stałe w pliku fcntl.h)
Þ przy otwarciu do zmian „+” (zapis i odczyt) należy zmienić pozycje zapisu po odczycie lub odczytu po zapisie za pomocą funkcji fseek (ewentualnie opróżniając bufory pośredniczące związane ze strumieniem za pomocą fflush)
· zamykanie plików:
deklaracja z stdio.h:
int fclose(FILE *stream), która:
Þ zamyka plik fizyczny dokonując zapisu wszystkich danych pozostawionych w buforach pośredniczących strumienia stream i usuwa z pamięci te bufory, jeżeli są domyślnymi;
Þ zwraca 0, jeśli plik został zamknięty lub EOF w przypadku wystąpienia błędu
· swobodny dostęp do pliku
Funkcja fseek ustawia wskaźnik pliku na dowolnym bajcie jego zawartości
deklaracja w pliku stdio.h:
int fseek(FILE *stream, long offset, int whence); gdzie:
stream - strumień, w którym fseek zmienia wskaźnik
offset - różnica w bajtach między położeniem whence wskaźnika pliku i nowym jego położeniem (ujemna oznacza „cofanie”). W trybie tekstowym, offset powinno być równe zero lub wartością funkcji ftell
whence - jedna z trzech wartości (SEEK_SET, SEEK_CUR, SEKK_END), gdzie:
SEEK_SET - początek pliku,
SEEK_CUR - bieżące położenie w pliku,
SEKK_END - koniec pliku
Funkcja zwraca 0, jeśli wskaźnik został prawidłowo przesunięty, w przeciwnym wypadku wartość różną od zera
· operacje buforowania
Funkcja fflush wysyła zawartość bufora do pliku związanego z danym strumieniem stream. Zawartość bufora automatyczne zostanie wysłana do pliku w przypadku zapełnienia.
deklaracja:
int fflush(FILE *stream);
Funkcja zwraca 0 w przypadku powodzenia, w przeciwnym wypadku EOF.
Model przetwarzania plików za pomocą standardowego wejścia- wyjścia
program C, zmienna FILE *stream i jej bufory Û system operacyjny Û dysk
1.1. Znakowe wejście - wyjście
Podstawowe operacje:
Þ getc pobiera znak ze strumienia i putc wysyła znak do strumienia
Deklaracja w stdio.h:
int getc(FILE *stream); int putc(int c, FILE *stream);
( int fputc(int c, FILE *stream); int putchar(int c); int fputchar(int c))
( int fgetc(FILE *stream); int getchar(void); int fgetchar(void))
Opis:
Þ getc zwraca następny znak ze strumienia wejściowego stream, dokonując konwersji do int i zwiększa wskaźnik pliku o 1,
Þ putc umieszcza w strumieniu stream znak c
Þ obie funkcje zwracają EOF jeśli wystąpił błąd lub osiągnięto koniec pliku dla getc
Przykłady:
// jednorazowo zapisuje jeden znak do pliku dyskowego skojarzonego ze strumieniem
#include <stdio.h> // dla standardowych I/O
#include <conio.h> // dla getche()...
hantajo