tutaj - KKiEM AGH

Transkrypt

tutaj - KKiEM AGH
Elementarne wiadomości o języku C
Oprac.: Zbigniew Rudnicki
1. Wprowadzenie
Pierwszą wersję języka C opracował Dennis Ritchie w roku 1972 (wykorzystując niektóre roz­
wiazania z opracowanych w latach1967-1970 języków BCPL oraz B). Pełny opis został zawarty w
książce Briana W. Kernighana i Dennisa M. Ritchie: "The C programming language" w roku 1978.
Język C opracowano głównie dla potrzeb programistów tworzących systemy operacyjne (w nim
napisano w r.1973 system UNIX) i dlatego jest znacznie trudniejszy i bardziej złożony niż np. BASIC
- przeznaczony dla początkujących, czy Matlab przeznaczony dla szerokich rzesz użytkowników.
Dalszy rozwój języka C doprowadził m.in. do ogłoszenia w roku 1988 standardu języka ANSI C.
W latach osiemdziesiątych Bjarne Stroustrup opracował znacznie rozszerzony, obiektowy i do­
stosowany do graficznego interfejsu język C++ w którym m.in. opracowano system Ms Windows.
Poniższy opis jest bardzo okrojony i uproszczony zarówno ze względu na znaczną trudnośc bar­
dziej zaawansowanych środków języka jak przewidziany niewielki udział tego języka w aktualnie
skonstruowanym programie nauczania oraz preferowaniem Matlaba.
1.1. Struktura programu
Program w języku C składa się z funkcji(1). Funkcja jest wydzieloną częścią programu, realizu­
jącą pewne zadanie. Główny program musi mieć postać funkcji o nazwie main() - od niej rozpoczyna
się wykonanie programu. Instrukcje składające się na treść funkcji zwaną jej "ciałem" umieszcza się w
nawiasach klamrowych { }. Nawiasy klamrowe { } są także używane wszędzie tam gdzie dwie lub
więcej instrukcji ma utworzyć blok, na przykład wewnątrz pętli lub w opcjach instrukcji warun­
kowej.
Dla ilustracji podaję najprostszy przykład programu:
/* Program wyświetla napis: WITAM */
#include <stdio.h>
main()
{
printf("WITAM \n");
}
Pozostałe objaśnienia:
 W dowolnych miejscach mogą być umieszczane komentarze ujęte między znakami /* ... */
 Na początku programu niezbędne są zazwyczaj tak zwane "dyrektywy preprocesora" rozpoczy­
nające się znakiem #. Dyrektywa #include pozwala wstawić zawartość określonego pliku (w tym
przypadku stdio.h), dokładnie w miejscu tej dyrektywy. W szczególności wstawiane są pod­
programy.
Plik stdio.h to tak zwany plik nagłówkowy (header - o czym świadczy rozszerzenie .h). Zawiera
on funkcje obsługi standardowego ("std") wejścia i wyjścia ("io" = input-otput) a wśród nich
definicję funkcji printf().
 Funkcja printf() kopiuje na ekran znaki zawarte między cudzysłowami " ", za wyjątkiem
sekwencji znaków specjalnych poprzedzonych znakiem backslash "\" i nazywanych "sekwencjami
1
) W innych językach program składa się z podprogramów wśród których jako funkcje definiowane są te które
zwracają pojedynczą wartość (tak jest np. w językach BASIC oraz FORTRAN) lub macierz (w Matlabie) a inne
definiowane są jako procedury, które nie muszą dawać w wyniku wartości liczbowych . W języku C są tylko
funkcje, dlatego wprowadzono typ void czyli "wartości których nie ma"
escape". Znak \n to polecenie zmiany linii - spowoduje, że kolejny wydruk (w tym przypadku na
ekranie) pojawi się w następnej linii.
Złożone programy składają się z wielu funkcji pełniących rolę podprogramów (zarówno funkcyjnych
jak i proceduralnych).
Oto kolejny przykład programu z objaśnieniami:
Program ten wczytuje długość w metrach, przelicza ją na centymetry i milimetry i wyświetla
na ekranie. Program kończy działanie po wprowadzeniu liczby ujemnej.
#include <stdio.h>
dołączenie pliku nagłówkowego stdio.h
main ()
funkcja main() - to główny blok programu
{
początek ciała funkcji main(), w nawiasach { }
int metr, centymetr, milimetr;
deklaracja typu zmiennych
printf (“ \n Podaj długość”);
w nowej linii wyświetla napis "Podaj..."
scanf ("%d" ,& metr);
wczytanie wartości całkowitej ("%d") do zmien­
nej metr
while (metr >=0)
początek pętli while() dla dodatnich wart. metr
{
ciało pętli umieszcza się w nawiasach {}
centymetr = 100*metr;
nadanie wartości zmiennej centymetr
milimetr=1000*metr;
nadanie wartości zmiennej milimetr
printf ("\n %d w metrach\n", metr);
wyświetlenie wyniku w metrach
printf ("%d w centymetrach \n", centymetr); wyświetlenie wyniku w centymetrach
printf ("%d w milimetrach \n", milimetr);
wyświetlenie wyniku w milimetrach
printf ("Podaj następną długość");
wyświetlenie napisu: "Podaj następną ..."
scanf ("%d", &metr);
wczytanie wartości do zmiennej metr
}
koniec pętli while
printf (" *** koniec programu *** \n");
wyświetlenie napisu: "***koniec programu.."
return (0)
funkcja main() zwraca zero
}
koniec ciała funkcji main()
1.2. Podstawowe pliki nagłówkowe
Pliki nagłówkowe zawierają deklaracje (tzw. prototypy) różnorodnych funkcji z bibliotek standar­
dowych niezbędnych dla działania konkretnego programu. Najczęściej dołączane dyrektywą #include
pliki nagłówkowe to: stdio.h, conio.h, stdlib.h, math.h, float.h
1.3. Typy. Deklaracje typów zmiennych
Wszystkie zmienne i struktury danych muszą być zadeklarowane na początku tej funkcji w której
są używane. Omówimy tylko deklaracje zmiennych prostych oraz tablic.
1.3.1. Zmienne proste i ich deklarowanie
Deklaracja zmiennych prostych składa się z nazwy typu i listy zmiennych:
lista zmiennych
nazwa_typu zmienna, zmienna, ...zmienna;
Przykład:
int metr, centymetr, milimetr;
deklaracja ta rezerwuje obszary pomięci dla trzech zmiennych:
metr, centymetr, milimetr;
typu całkowitego - o czym świadczy nazwa typu: int.
2
Oprócz konieczności zadeklarowania trzeba jeszcze dobrać typy odpowiednie do
roli zmiennych i operacji w jakich mają brać udział. Na przykład wskaźniki (indeksy)
elementów wektorów i macierzy muszą być typu całkowitego, a zmienne dla których ma sens
dzielenie, pierwiastkowanie i inne działania dające wynik niecałkowity - muszą być typu
rzeczywistego.
W języku C są cztery podstawowe proste typy zmiennych o nazwach:
 char - znak,
 int - wartości całkowite,
 float oraz double - wartości rzeczywiste
 void - typ bezwartościowy (to znaczy brak zmiennej tam gdzie teoretycznie powinna być,
na przykład brak argumentu funkcji lub jej rezultatu)
Typy te mogą być zmodyfikowane przez poprzedzenie nazwy typu (w deklaracji) jednym ze słów:
• unsigned - bez znaku;
• short - krótki
• long - długi
Wymienione typy scharakteryzowano w tabeli:
Nazwa typu
void
Typ
Zakres
brak wartości
Całkowite używane dla znaków drukarskich:
char
całkowity
-128...127
unsigned char
całkowity
0...255
Całkowite
int
całkowity
-2^31...2^31-1
unsigned int
całkowity
0...2^32
short int
całkowity
-32768...32767
unsigned short int
całkowity
0...65535
long int
całkowity
-2^31...2^31-1
unsigned long int
całkowity
0...2^32
Rzeczywiste
float
rzeczywisty
6 znaków precyzji
double
rzeczywisty
10 znaków precyzji
Bajtów
1
1
4 (lub 2)
4 (lub 2)
2
2
4
4
4
8
1.3.2. Tablice i deklaracje tablic
Tablica jednowymiarowa czyli wektor jest zbiorem ponumerowanych elementów jed­
nakowego typu. Numer pierwszego elementu w tablicy jest zawsze równy zero.
Tablice muszą - tak jak inne zmienne - być deklarowane. Deklaracja tablicy zawiera:
 nazwę typu
 listę nazw tablic z ich wymiarami - czyli po każdej nazwie w nawiasach
prostokątnych muszą być podane maksymalne przewidywane wartości wskaź­
ników (zwanych też indeksami lub numerami elementów).
Przykład deklaracji dwu tablic o nazwach "a" oraz "wektor":
int a[5], wektor[10];
Tablicę można także inicjować podając w deklaracji po jej nazwie i znaku równości listę war­
tości oddzielonych przecinkami i zamkniętych w nawiasach klamrowych.
Przykład:
int a1[5] = {1, 5, 3, 4, 2};
W programach posługujemy się elementami tablic określanymi przez nazwę tablicy
oraz indeksy ujęte w nawiasy kwadratowe. Jako indeks czyli numer elementu może służyć
3
stała całkowita, zmienna typu całkowitego lub dowolne wyrażenie, którego wynikiem jest
liczba całkowita.
Przykłady:
a[5] = 10; b[i+1] = b[i]*2;
Możliwe jest zadeklarowanie tablicy tablic (odpowiadającej tablicy dwu- lub więcej wy­
miarowej):
int a[10][15];
Powyższa instrukcja deklaruje 10-cio elementową tablicę a, której polami są piętnasto
elementowe tablice zmiennych typu int. Przy odwoływaniu się do elementów tablicy najpierw
podaje się numer elementu pierwszej tablicy, potem numer elementu wewnątrz tej tablicy:
a[4][5] = 10;
1.4. Stałe, zmienne, wyrażenia arytmetyczne, instrukcje przypisania
Uwaga: duże i małe litery w języku C są rozróżniane!
1.4.1. Stałe
Deklarowanie stałych jest możliwe przy pomocy dyrektyw #define w których podaje się na­
zwę stałej i oddzieloną odstępem jej wartość. Np.:
# define NUMBER 3.15
# define NUMBER1 3.0
# define CHARACTER ‘A’
# define STRING “ABC”
1.4.2. Identyfikatory (nazwy)
Jeżeli piszemy program musimy wybrać nazwy dla zmiennych, funkcji i innych obiek­
tów. Identyfikator w C musi spełniać następujące wymagania:
musi się zaczynać od litery (A do Z, a do z) lub też od znaku podkreślenia _;
musi się składać z liter (A do Z, a do z), cyfr lub też od znaków podkreślenia _;
nie może być słowem kluczowym (Słowo kluczowe to takie słowo jak int czy while,
które ma specjalne znaczenie).
1.4.3. Operatory arytmetyczne
Priorytet
3
3
2
2
2
1
1
Operator
+
*
/
%
+
++ oraz --
Uwagi
jednoargumentowy jednoargumentowy +
mnożenie
dzielenie (rzeczywiste lub całkowite)
reszta z dzielenia
odejmowanie
dodawanie
objaśniono poniżej
Operator ++ oraz - Operator ++ użyty jako przyrostek to tzw. postinkrementacja, natomiast użyty jako
przedrostek to tzw. preinkrementacja. Różnicę w ich działaniu pokazuje przykład:
Załóżmy, że zmienna a ma wartość pięć i wykonujemy taką oto instrukcję:
c = a++;
4
W takim przypadku zmiennej c zostanie przypisana wartość zmiennej a (czyli pięć) i dopiero
po tym przypisaniu zmienna a zostanie zwiększona o jeden. Czyli w efekcie po wykonaniu tej
instrukcji zmienna c będzie zawierała wartość pięć, natomiast zmienna a będzie równa sześć.
Teraz przy założeniach takich samych jak powyżej wykonujemy taką instrukcję:
c = ++a;
W takim przypadku najpierw zmienna a zostanie zwiększona o jeden (czyli teraz będzie rów­
na sześć) i następnie ta wartość będzie przypisana zmiennej c. Czyli w efekcie po wykonaniu
tej instrukcji obie zmienne będą równe sześć.
Analogicznie działa operator -- tylko zamiast zwiększania, zmniejsza wartość o jeden.
1.5. Funkcje wejścia i wyjście (liczbowe i tekstowe)
Podstawowymi funkcjami dla wyprowadzania wyników są printf oraz fprintf.
Funkcja printf ma najczęściej ogólną postać następującą:
printf("format", lista_zmiennych)
gdzie:
lista_zmiennych - to ciąg nazw zmiennych lub elementów tablic pooddzielanych przecinkami
"format" - to ciąg znaków umieszczony między cudzysłowami i zawierający:
 dowolne teksty kopiowane na ekran
 zaczynające się od znaku backslash "\" - sekwencje znaków specjalnych (m.in. steru­
jących drukowaniem), nazywane "sekwencjami escape". W szczególności znak \n to po­
lecenie zmiany linii - spowoduje, że kolejny wydruk pojawi się w następnej linii.
 zaczynające się od znaku "%" opisy formatów w jakich mają być wyprowadzane war­
tości zmiennych
Na przykładach poniżej objaśniono najprostsze i najczęściej używane formaty:
%d - dla wartości typu całkowitego
%6d - dla wartości typu całkowitego, która ma zająć co najmniej 6 znaków
%f
- dla wartości typu rzeczywistego (typ float)
%8.4f - dla wartości typu rzeczywistego (typ float), która ma zająć co najmniej 8 znakówa
w tym 4 miejsca po kropce dziesiętnej (nie przecinek tylko kropka zwyczajem anglosaskim)
1.6. Wyrażenia logiczne i instrukcja warunkowa IF
Operatory relacji:
Operator
==
>
>=
<
<=
!=
Znaczenie
równe
większe
większe lub równe
mniejsze
mniejsze lub równe
nierówne
Instrukcja if jest stosowana by komputer mógł - zależnie spełnienia lub nie spełnienia określo­
nego warunku - wybrać odpowiednią sekwencję operacji. Najprostsza z form instrukcji if:
if (warunek)
{
blok instrukcji;
}
umożliwia wykonanie {bloku instrukcji} tylko wtedy gdy jest spełniony podany warunek.
Warunek jest wyrażeniem logicznym i musi być zawarty w nawiasach okrągłych, a blok instrukcji jest
ujęty w nawiasy klamrowe, które pomija się gdy blok składa się tylko z jednej instrukcji.
5
Najpierw komputer określa czy ma wartość logiczną "prawda" czy "fałsz". Jeżeli warunek ma
wartość logiczną "prawda" to zostaje wykonany {blok instrukcji} i sterowanie przechodzi do instrukcji
następnej.
Druga forma instrukcji if realizuje wykonanie {blok instrukcji 1} gdy podany warunek
ma wartość "prawda" natomiast {blok instrukcji 2} gdy ma wartość "fałsz":
if (wyrażenie)
{
blok instrukcji 1;
}
else
{
blok instrukcji 2;
}
1.7. Pętle
1.7.1. Pętla FOR
for(początek; warunek; zmiana)
{
instrukcje wielokrotnie wykonywane
}
Przykład:
for (fahr=0; fahr<=300; fahr=fahr+20)
printf("Temperatura w stopniach Fahrnheita %3d w St.Celsjusza %6.1f\n",fahr, (5.0/9.0)*(fahr-32));
Instrukcja continue
Instrukcja continue może wystąpić tylko wewnątrz instrukcji pętli i powoduje przeskok
do końca pętli czyli do sprawdzenia możliwości dalszego wykonywania (kontynuacji) pętli.
Instrukcja break
Instrukcja break może wystąpić tylko wewnątrz pętli i powoduje wyskoczenie z tej pętli.
1.7.2. Pętla WHILE
while(warunek)
{
}
instrukcje wielokrotnie wykonywane
Pętla ta powtarza instrukcje zawarte w nawiasach klamrowych tak długo dopóki spełniony jest
warunek.
6

Podobne dokumenty