ISO/ANSI C dostęp do plików ISO/ANSI C. ISO/ANSI C dostęp do plików. ISO/ANSI C dostęp do plików. ISO/ANSI C dostęp do plików

Podobne dokumenty
ISO/ANSI C dostęp do plików ISO/ANSI C. ISO/ANSI C dostęp do plików. ISO/ANSI C dostęp do plików. ISO/ANSI C dostęp do plików

ISO/ANSI C dostęp do plików ISO/ANSI C. ISO/ANSI C dostęp do plików. ISO/ANSI C dostęp do plików. ISO/ANSI C dostęp do plików

Biblioteka standardowa - operacje wejścia/wyjścia

Funkcje zawarte w bibliotece < io.h >

Wskaźniki do funkcji. Wykład 11. Podstawy programowania ( język C ) Wskaźniki do funkcji (1) Wskaźniki do funkcji (2)

Funkcje zawarte w bibliotece < io.h >

ISO/ANSI C dostęp do plików. ISO/ANSI C dostęp do plików. ISO/ANSI C klasy pamięci ISO/ANSI C. ISO/ANSI C klasy pamięci. ISO/ANSI C klasy pamięci

ISO/ANSI C klasy pamięci ISO/ANSI C. ISO/ANSI C klasy pamięci. ISO/ANSI C klasy pamięci. Pamięć programu. ISO/ANSI C klasy pamięci

Tablice w argumentach funkcji. Tablicy nie są przekazywane po wartości Tablicy są przekazywane przez referencje lub po wskaźniku

ISO/ANSI C - funkcje. Funkcje. ISO/ANSI C - funkcje. ISO/ANSI C - funkcje. ISO/ANSI C - funkcje. ISO/ANSI C - funkcje

Operacje na plikach. Informatyka. Standardowe strumienie wejścia i wyjścia

Ghost in the machine

Struktury. Przykład W8_1

Obsługa plików. Laboratorium Podstaw Informatyki. Kierunek Elektrotechnika. Laboratorium Podstaw Informatyki Strona 1. Kraków 2013

Ćwiczenie 4. Obsługa plików. Laboratorium Podstaw Informatyki. Kierunek Elektrotechnika. Laboratorium Podstaw Informatyki Strona 1.

Programowanie Proceduralne

Programowanie proceduralne INP001210WL rok akademicki 2018/19 semestr letni. Wykład 6. Karol Tarnowski A-1 p.

Podstawy programowania w języku C++

Wykład VI. Programowanie. dr inż. Janusz Słupik. Gliwice, Wydział Matematyki Stosowanej Politechniki Śląskiej. c Copyright 2014 Janusz Słupik

Wstęp do programowania INP001213Wcl rok akademicki 2017/18 semestr zimowy. Wykład 12. Karol Tarnowski A-1 p.

Program wykonujący operację na plikach powinien zachować schemat działania zapewniający poprawną pracę:

۰ Elementem jednostkowym takiego pliku jest bajt. ۰ Format pliku binarnego: [bajty pliku][eof]

W języku C każdy plik fizyczny jest ciągiem bajtów, z których każdy może być niezależnie odczytany. Borland 01234

Języki programowania. Przetwarzanie plików amorficznych Konwencja języka C. Część siódma. Autorzy Tomasz Xięski Roman Simiński

Pliki. Informacje ogólne. Obsługa plików w języku C

Pliki. Informacje ogólne. Obsługa plików w języku C

Struktura programu. Projekty złożone składają się zwykłe z różnych plików. Zawartość każdego pliku programista wyznacza zgodnie z jego przeznaczeniem.

Stałe i zmienne znakowe. Stała znakowa: znak

Plik jest reprezentowany przez strumień znaków (bajtów) o zmiennej długości. Koniec strumienia identyfikowany jest znacznikiem końca pliku EOF.

MATERIAŁY POMOCNICZE PODSTAWY PROGRAMOWANIA Na podstawie: Programowanie w C - Stworzone na Wikibooks, bibliotece wolny podręczników

Argumenty wywołania programu, operacje na plikach

Podstawy programowania w języku C++

Podstawy programowania. Wykład 6 Wskaźniki. Krzysztof Banaś Podstawy programowania 1

Lab 9 Podstawy Programowania

INFORMATYKA Studia Niestacjonarne Elektrotechnika

Języki programowania. Karolina Mikulska-Rumińska Pokój 573, tel Konsultacje wtorek 9-10.

Wskaźniki. Przemysław Gawroński D-10, p marca Wykład 2. (Wykład 2) Wskaźniki 8 marca / 17

Wskaźniki. Programowanie Proceduralne 1

Programowanie proceduralne INP001210WL rok akademicki 2015/16 semestr letni. Wykład 6. Karol Tarnowski A-1 p.

Wskaźniki w C. Anna Gogolińska

Programowanie Procedurale. Pliki w języku C++

Temat: Dynamiczne przydzielanie i zwalnianie pamięci. Struktura listy operacje wstawiania, wyszukiwania oraz usuwania danych.

KURS C/C++ WYKŁAD 6. Wskaźniki

Łącza nienazwane(potoki) Łącza nienazwane mogą być używane tylko pomiędzy procesami ze sobą powiązanymi.

wer. 7 z drobnymi modyfikacjami Wojciech Myszka :48:

METODY I JĘZYKI PROGRAMOWANIA PROGRAMOWANIE STRUKTURALNE. Wykład 02

Programowanie w językach wysokiego poziomu

Spis treści PLIKI BINARNE W JĘZYKU C. Informatyka 2. Instrukcja do pracowni specjalistycznej z przedmiotu. Numer ćwiczenia INF23

Podstawy programowania komputerów

Uzupełnienie dot. przekazywania argumentów

Podstawy programowania skrót z wykładów:

Wskaźniki. Informatyka

4. Tablica dwuwymiarowa to jednowymiarowa tablica wskaźników do jednowymiarowych tablic danego typu.

wykład III uzupełnienie notatek: dr Jerzy Białkowski Programowanie C/C++ Język C - zarządzanie pamięcią, struktury,

Co to jest sterta? Sterta (ang. heap) to obszar pamięci udostępniany przez system operacyjny wszystkim działającym programom (procesom).

Obsługa plików. Systemy Operacyjne 2 laboratorium. Mateusz Hołenko. 25 września 2011

Tablice, funkcje - wprowadzenie

Języki i metodyka programowania. Typy, operatory, wyrażenia. Wejście i wyjście.

Podstawy programowania w języku C++

Spis treści JĘZYK C - PLIKI BINARNE. Informatyka 2. Instrukcja do pracowni specjalistycznej z przedmiotu. Numer ćwiczenia INF30

Lab 8. Tablice liczbowe cd,. Operacje macierzowo-wektorowe, memcpy, memmove, memset. Wyrażenie warunkowe.

Formatowane (tekstowe) wejście/wyjście. Binarne wejście/wyjście.

Lekcja 10. Uprawnienia. Dołączanie plików przy pomocy funkcji include() Sprawdzanie, czy plik istnieje przy pmocy funkcji file_exists()

main( ) main( void ) main( int argc, char argv[ ] ) int MAX ( int liczba_1, liczba_2, liczba_3 ) źle!

Podstawy programowania. Wykład Funkcje. Krzysztof Banaś Podstawy programowania 1

Tablice deklaracja, reprezentacja wewnętrzna

Programowanie w językach

PRZYKŁADY OPERACJI PLIKOWYCH z wykorzystaniem biblioteki <stdio.h>

Spis treści PLIKI BINARNE W JĘZYKU C. Informatyka 2. Instrukcja do pracowni specjalistycznej z przedmiotu. Numer ćwiczenia INF23

4. Pliki Informacje ogólne o dostępie do plików w PHP Sprawdzanie istnienia pliku file_exists()

Laboratorium Systemów Operacyjnych. Ćwiczenie 4. Operacje na plikach

Globalne / Lokalne. Wykład 15. Podstawy programowania (język C) Zmienne globalne / lokalne (1) Zmienne globalne / lokalne (2)

Podstawy programowania w języku C++

Wskaźniki i dynamiczna alokacja pamięci. Spotkanie 4. Wskaźniki. Dynamiczna alokacja pamięci. Przykłady

ISO/ANSI C - funkcje. Funkcje. ISO/ANSI C - funkcje. ISO/ANSI C - funkcje. ISO/ANSI C - funkcje. ISO/ANSI C - funkcje

Wskaźniki. nie są konieczne, ale dają językowi siłę i elastyczność są języki w których nie używa się wskaźników typ wskaźnikowy typ pochodny:

Materiał Typy zmiennych Instrukcje warunkowe Pętle Tablice statyczne Wskaźniki Tablice dynamiczne Referencje Funkcje

Struktury czyli rekordy w C/C++

Laboratorium 6: Dynamiczny przydział pamięci. dr inż. Arkadiusz Chrobot dr inż. Grzegorz Łukawski

7 Przygotował: mgr inż. Maciej Lasota

Programowanie w języku C++

Operacje na plikach (niskiego poziomu) < IO.H >

DYNAMICZNE PRZYDZIELANIE PAMIECI

Wprowadzenie do programowania w języku C

Metodyka i Technika Programowania 1

Języki i metodyka programowania. Wskaźniki i tablice.

Języki i metody programowania I

Wstęp do programowania INP001213Wcl rok akademicki 2018/19 semestr zimowy. Wykład 4. Karol Tarnowski A-1 p.

4. Wyrzuć wyjątek jeśli zmienna ist nie istnieje bloki: try, catch i wyrzucanie wyjątku

Katedra Elektrotechniki Teoretycznej i Informatyki. wykład 9 - sem.iii. Dr inż. M. Czyżak

Ćwiczenie nr 6. Poprawne deklaracje takich zmiennych tekstowych mogą wyglądać tak:

Podstawy programowania w języku C++

Stałe, tablice dynamiczne i wielowymiarowe

Wstęp do programowania 1

Podstawy programowania 1

C++ - przeciążanie operatorów. C++ - przeciążanie operatorów. C++ - przeciążanie operatorów. C++ - przeciążanie operatorów

Język C zajęcia nr 11. Funkcje

Podstawy informatyki. Informatyka stosowana - studia niestacjonarne. Grzegorz Smyk. Wydział Inżynierii Metali i Informatyki Przemysłowej

Język C++ Różnice między C a C++

Transkrypt:

ISO/ANSI C Dostęp do plików w trybie tekstowym znak po znaku Czytanie z pliku int fgetc( FILE *stream ); char buffer[81]; int i, ch; <stdio.h> if((stream = fopen("test.txt","r")) == NULL ) exit( 0 ); ch = fgetc( stream ); for(i=0; (i < 80 ) && (feof(stream)==0);i++) { buffer[i] = (char)ch; ch = fgetc( stream ); buffer[i] = '\0'; printf( "%s\n", buffer ); 83 Czytanie z pliku Pisanie do pliku int fputc( int c, FILE *stream ); int fgetc( FILE *stream ); /* zaimplementowane jako funkcja */ char strptr[] = Asta la vista!\n"; char *p; int getc( FILE *stream ); /* zaimplementowane jako funkcja i makro */ Działa tak samo. if( (stream = fopen( "crt_test.txt", "w" )) == NULL ) exit( 0 ); p = strptr; while( (*p!= '\0') && fputc( *(p++), stream )!= EOF ); 84 85 fgetc, getc i putc są niepraktyczne, jeżeli mamy działać na danych tekstowych, reprezentujących wartości o znaczeniu leksykalnym (np. słowa, liczby). fgetc, getc i putc wymagają w programie dodatkowego kodu służącego do analizy wczytanych znaków, aby prawidłowo określić, czy jest to np. liczba oraz czy ta liczba jest poprawnie zapisana. tymczasem są inne funkcje biblioteczne, które taką analizę mają już wbudowaną w sobie i służą np. do odczytywania całych liczb lub całych słów. Dlatego, o ile to możliwe, należy jednak stosować formatowany dostęp do plików. Pisanie do pliku serii znaków int fputs( const char *string, FILE *stream ); char strptr[] = Asta la vista!\n"; if((stream = fopen("crt_test.txt", "w")) == NULL) exit( 0 ); fputs( strptr, stream ); 86 87 1

Dygresja: fputs vs. puts fputs pisze do wskazanego strumienia (pierwszy argument wywołania) puts pisze do standardowego strumienia wyjściowego (okno konsoli) puts dołącza na końcu znak nowej linii '\n' Manipulowanie wskaźnikiem bieżącego elementu w pliku 88 Czytanie z pliku Po otwarciu pliku otrzymujemy prawo dostępu do danych w pliku Dane reprezentowane są jako strumień Po otwarciu mamy prawo do odczytu pierwszego elementu w pliku (pierwszego bajtu) Aktualną pozycję w pliku, z której w danej chwili mamy prawo czytać, określa wskaźnik pliku Po odczycie wskaźnik pliku przesuwa się w przód o tyle bajtów, ile zostało odczytanych Wskaźnika nie można cofać (w zasadzie..) int fseek( FILE *stream, long offset, int origin ); <stdio.h> stream wskaźnik do otwartego pliku offset liczba bajtów od miejsca wskazywanego przez origin origin stała: SEEK_CUR bieżąca pozycja wskaźnika SEEK_END koniec pliku SEEK_SET początek pliku fseek zwraca zero, jeżeli przesunięcie wskaźnika pliku się powiodło, lub wartość niezerową w przeciwnym przypadku 90 91 int fseek( FILE *stream, long offset, int origin ); <stdio.h> fseek to funkcja ryzykowna, np.: kiedy plik jest otwarty w trybie do dołączania ( a lub a+ ), bieżącą pozycją wskaźnika w pliku jest rezultat ostatniej operacji We/Wy. Jeżeli takiej operacji jeszcze nie było (plik został tylko otwarty), wskaźnik wskazuje na pierwszy element pliku (!) dla plików otwartych w trybie tekstowym znaki nowej linii (CR-LF) wprowadzają funkcje fseek w błąd i mogą powodować nieoczekiwane rezultaty jej działania. Poprawne działanie jest gwarantowane tylko gdy offset jest ustawione na 0 (położenie określone jest tylko przez ostatni parametr: origin). 92 char line[81]; int result; stream = fopen( "fseek.out", "w+" ); if( stream == NULL ) printf( "Plik nie został otwarty\n" ); fprintf( stream, "fseek przesunie tutaj: abrakadabra.\n" ); result = fseek( stream, 23L, SEEK_SET); if( result ) printf( "Fseek nie powiodl sie" ); printf( "Wskaznik jest ustawiony w polowie linii.\n" ); fscanf( stream, "%s", line ); printf( "%s", line ); /* co pojawi się w oknie konsoli? */ 93 2

void rewind( FILE *stream ); przesuwa wskaźnik pliku na początek pliku Działa tak samo jak: fseek( stream, 0L, SEEK_SET ); ale nie zwraca wartości informującej czy przesunięcie wskaźnika się powiodło int data1, data2; data1 = 1; data2 = -37; if( (stream = fopen( "crt_rewind.out", "w+" ))!= NULL ) { fprintf( stream, "%d %d", data1, data2 ); printf( "Wartosci zapisane to: %d i %d\n", data1, data2 ); rewind( stream ); fscanf( stream, "%d %d", &data1, &data2 ); printf( "Wartosci odczytane to: %d i %d\n", data1, data2 ); /* co pojawi się w oknie konsoli? */ 94 95 int fflush( FILE *stream ); Wypchnięcie z tzw. strumienia (tj. bufora pliku) znajdujących się tam danych (jeżeli pomyślne, zwraca zero, jeżeli nie EOF) Jeżeli plik był otwarty do zapisu, dane są natychmiast przepisywane do pliku. Jeżeli do odczytu dane z bufora są tracone, a bufor staje się pusty fflush(null) wymusza zapisanie do plików danych ze wszystkich strumieni otwartych w trybie do zapisu Strumienie są zarządzane przez system operacyjny, który sam decyduje, kiedy przepisać dane z rzeczywistego pliku (np. albo w momencie zamykania pliku, albo kiedy już bufor jest zapełniony, albo też kiedy program kończy się poprawnie jednak bez wywołania polecenia zamykającego plik) Oprócz strumieni otwieranych przez użytkownika istnieją trzy strumienie standardowe otwierane przez system i dostępne w programie (biblioteka <stdio.h>): stdin standardowe wejście, np. klawiatura stdout standardowe wyjście, np. okno konsoli stderr standardowy strumień dla komunikatów o błędach, np. okno konsoli Te trzy zmienne są const i nie można ich zapisać innymi wartościami. Można je natomiast przekierować używając funkcji freopen 96 97 FILE *freopen( const char *path, const char *mode, FILE *stream ); Zamyka plik przypisany do aktualnie otwartego strumienia i przypisuje zmienną stream do pliku wskazywanego przez path Typowo funkcja jest używana do przekierowywania strumieni standardowych stdin, stdout, stderr Argument mode przyjmuje takie same wartości jak w funkcji fopen int fgetpos(file *stream, fpos_t *pos); int fsetpos(file *stream, const fpos_t *pos); Odczyt aktualnej pozycji wskaźnika pliku lub przesuniecie go w nowe miejsce. Jeżeli pomyślnie, funkcja zwraca zero. Pozycja wskaźnika musi być przechowywana w zmiennej typu fpos_t. Pozycja wskaźnika jest interpretowana jako numer bajtu. stream = freopen( "freopen.out", "w", stderr ); 98 99 3

fpos_t pos; char buffer[20]; if( (stream = fopen( "crt_fgetpos.txt", "rb" )) == NULL ) printf( "Trouble opening file\n" ); pos = 14; if( fsetpos( stream, &pos )!= 0 ) perror( "fsetpos error" ); Uwaga: jeżeli zdecydowano otworzyć plik w trybie r+, w+ lub a+ i następuje zmiana z czynności zapisu do czynności odczytu, lub odwrotnie, to musi być najpierw wywołana funkcja fflush, fsetpos, fseek, lub rewind, która prawidłowo ustawi wskaźnik pliku. fread( buffer, sizeof( char ), 10, stream ); printf( "10 bytes at byte %I64d: %.10s\n", pos, buffer ); 100 101 Tryb binarny size_t fread( void *buffer, size_t size, size_t count, FILE *stream ); size_t fwrite( const void *buffer, size_t size, size_t count, FILE *stream ); Odczytuje lub zapisuje określoną liczbę porcji danych do/z bufora wskazywanego przez buffer z/do pliku wskazywanego przez stream Zwraca liczbę porcji wczytanych/zapisanych. Jeżeli liczba nie zgadza się z zadeklarowaną, to w przypadku odczytu znaczy, że być może w pliku było mniej danych niż się spodziewano, lub wystąpił błąd odczytu (należy użyć funkcji feof lub ferror, żeby to rozstrzygnąć) 103 ISO/ANSI C Klasy pamięci Zmienne mogą być definiowane z modyfikatorami: auto, extern, static auto zmienna lokalna istniejąca tylko w obrębie bloku: tworzona w momencie gdy sterowanie wchodzi do danego bloku i usuwana gdy opuszcza (wszystkie zmienne zadeklarowane w obrębie bloku są z definicji lokalne, dlatego tego modyfikatora się nie używa). extern deklaracja zmiennej zdefiniowanej w innym pliku (dla kodu programu, który jest podzielony na pliki) static zmienne statyczne, istniejące w jednym egzemplarzu 105 4

Czym różnią się zmienne static od globalnych? Zmienne static są widziane tylko w module/pliku, w którym zostały zadeklarowane; nie można się do nich odwołać z innego pliku za pomocą extern zmienna static zadeklarowana w bloku nie jest usuwana po wyjściu z tego bloku. Po powrocie sterowania do tego bloku wartość zmiennej static jest zachowana 106 zmienne volatile Zmienna może ulec zmianie bez wiedzy programu, np. ponieważ reprezentuje obszar danych będący pod kontrolą interfejsu do urządzenia zewnętrznego, lub gdy programujemy wielowątkowo i zmienna pozwala na wymianę informacji między wątkami Kompilator traktują ją jako niepewną, tj. przed każdym użyciem odczytuje jej wartość z pamięci (a nie np. z cache u), a każda modyfikacja musi zostać wykonana przed przystąpieniem do wykonania następnych instrukcji (żadnego przyspieszania wykonania programu przy pomocy potokowego wykonania instrukcji przez zaawansowany procesor, itp.) 107 zmienne const wartość zmiennej nie może ulec zmianie po jej utworzeniu jest inicjalizowana w momencie jej definiowania Komentarz na marginesie: modyfikator const wykorzystywany jest również przy deklarowaniu argumentów funkcji dla zagwarantowania nietykalności zmiennych podawanych w argumentach wykonania, np.: char *strcpy( char *strdestination, const char *strsource ); Uwaga: typ char* to nie to samo co const char* ISO/ANSI C Zmienne dynamiczne 108 Zmienne deklarowane w kodzie programu są tworzone: w momencie uruchomienia programu (zmienne globalne), lub w momencie wejścia sterowania do bloku instrukcji, w którym zostały zadeklarowane (zmienne lokalne) Zmienne te są identyfikowane przez nazwy Programista musi przewidzieć, ile zmiennych będzie potrzebował dla swojego algorytmu A co robić, jeżeli zdarzy się, że programista nie jest w stanie tego przewidzieć? Sytuacje, kiedy nie wiemy nic pewnego o rozmiarze zbioru danych, na którym będziemy operować: praca na danych z pliku (rozmiar pliku nie jest znany) wczytywanie danych, co do których nie znamy ograniczenia na ilość (wprowadzanie faktur, produktów do cennika) odbiór danych z interfejsu zewnętrznego (billingi telefoniczne, w medycynie: pomiary ciągłe stanu pacjenta temperatura, tętno, itp.) Algorytm musi być przygotowany na to, że dopiero w trakcie działania dowie się, jaki jest rozmiar danych roboczych i musi umieć odpowiednio do tego rozmiaru na bieżąco przygotować struktury danych na jego przyjęcie 110 111 5

Dynamiczne dostosowanie się programu do danych wejściowych jest możliwe z pomocą zmiennych dynamicznych. Zmienne dynamiczne są tworzone w trakcie działania programu za pomocą polecenia alokacji danych. Ich rozmiar może być określony dopiero czasie działania programu (nie musi być wcześniej znany programiście), a po ich wykorzystaniu, zaalokowany obszar pamięci można zwolnić i z powrotem oddać do dyspozycji systemowi. Alokowanie zmiennej dynamicznej (<stdlib.h> i <malloc.h>): void *malloc( size_t size ); Funkcja zwraca adres do obszaru pamięci o rozmiarze size. Zwracany typ void* pozwala na zapisanie wyniku do zmiennej wskaźnikowej dowolnego typu. char *string = malloc( 80 ); if( string == NULL ) printf("brak wystarczającej ilości pamięci\n"); else printf("zaalokowano zmienną dynamiczną\n"); Aby zagwarantować przenośność kodu, zamiast samemu obliczać całkowity rozmiar pamięci, lepiej wykorzystać funkcję sizeof: string = malloc( 80 *sizeof(char) ); 112 113 Usuwanie zaalokowych zmiennych Kiedy zmienna przestaje być potrzebna zaalokowane zasoby pamięci należy zwolnić. void free( void *memblock ); Argumentem wywołania jest wskaźnik na zmienną. Zapominanie o zwalnianiu zaalokowanych zasobów jest typowym błędem, powoduje, że w trakcie pracy aplikacji zużywa ona coraz więcej i więcej zasobów. Takie zjawisko jest nazywane wyciekaniem pamięci. Usuwanie zaalokowych zmiennych char *string = malloc( 80 ); if( string == NULL ) printf( Brak wystarczającej ilości pamięci\n" ); printf( Zaalokowano zmienną dynamiczną\n" ); /* kod programu wykorzystujący zaalokowaną zmienną */ free( string ); 114 115 Zgubienie wskaźnika do zmiennej dynamicznej powoduje całkowitą utratę kontroli nad tą zmienną, ale nie zwalnia zasobów. Przykład z tablicami dynamicznymi: double * t1 = malloc(100*sizeof(double)); double * t2 = malloc(100*sizeof(double)); /* zamieniamy się tablicami */ t1 = t2; t2 = t1; /* Bez sensu. Tak się nie robi.. */ /* prawidłowo zamieniamy się tablicami */ double *t3; /* tworzymy zmienną pomocniczą t3 */ t3 = t1; t1 = t2; t2 = t3; /* zamieniamy */ Dwuwymiarowe tablice dynamiczne Alokowanie: int i; double **t1 = malloc(100*sizeof(double*)); for (i=0; i<100; i++) t1[i] = malloc(100*sizeof(double)); Zwalnianie: int i; for (i=0; i<100; i++) free( t1[i] ); free( t1 ); 116 117 6

Alokowanie i inicjalizacja zerami void *calloc( size_t num, size_t size ); Zmiana rozmiaru zaalokowanego bloku void *realloc(void *memblock, size_t size); long *buffer; buffer = calloc( 40, sizeof( long ) ); if (buffer == NULL) { printf( "Can't allocate memory\n" ); exit(1); /* działania na zmiennej buffer */ free( buffer ); long *buffer; buffer = malloc( 1000 * sizeof( long ) ); if (buffer == NULL) exit( 1 ); /* Realokacja */ buffer = realloc( buffer, 2000 * sizeof( long )); if (buffer == NULL) exit( 1 ); 118 119 void *memcpy( void *dest, const void *src, void *memmove( void *dest, const void *src, Kopiuje z obszaru pamięci wskazanego przez src liczbę count bajtów do obszaru pamięci wskazanego przez dest memcpy szybsze (różnica widoczna przy wielkich rozmiarach danych kopiowanych po wielokroć) memmove zabezpiecza poprawne działanie w przypadku, kiedy wskazane obszary pamięci mogą się częściowo pokrywać 120 void *memcpy( void *dest, const void *src, void *memmove( void *dest, const void *src, char tab[] = "Lorem ipsum dolor sit amet, consectetur adipisicing elit"; char*ptab = calloc(100,sizeof(char)); int i = sizeof(tab); memcpy(ptab,tab, i); /* tak jest szybciej: */ memmove(tab+5,tab, i); /* tak bezpieczniej: */ 121 Porównanie znaków w dwóch buforach: int memcmp( const void *buf1, const void *buf2, char first[] = "12345678901234567890"; char second[] = "12345678901234567891"; int result = memcmp( first, second, 19 ); if( result < 0 ) printf( Pierwszy jest mniejszy niż drugi.\n" ); else if( result == 0 ) printf( Pierwszy i drugi są równe.\n" ); else printf( Pierwszy jest większy niż drugi.\n" ); Wypełnienie bufora znakami: void *memset( void *dest, int c, char buffer[] = To tylko taki mały test memset"; printf( Przed: %s\n", buffer ); memset( buffer, '*', 14 ); printf( Po: %s\n", buffer ); Przed: To tylko taki mały test memset Po: **************mały test memset 122 123 7