Jeśli nigdy nie korzystałeś z C++, a chcesz zacząć (bez wczytywania się
w setki nudnych akapitów), to znalazłeś się w odpowiednim miejscu.
Zaczynamy bowiem kurs programowania dla absolutnie początkujących.
Każda część jest podzielona na rozdziały, na końcu których znajdować
się będzie podsumowanie (treści do zapamiętania) oraz zadanie do
indywidualnego przemyślenia. Na początku kursu niektóre aspekty języka
nie zostaną zbyt szczegółowo opisane, aby nie narobić za dużo
zamieszania (np. różnica pomiędzy deklaracją a definicją).
Aby pisać programy w jakimkolwiek języku potrzebujesz kompilatora.
Najogólniej rzecz ujmując jest to aplikacja, która przetłumaczy to, co
napiszesz (w naszym wypadku jest to C++) na język zrozumiały dla
komputera (abyś mógł uruchomić program i obejrzeć efekty swej pracy).
Jeśli nie spotkałeś się z narzędziem tego typu nigdy wcześniej -
przeczytaj dodatek z końca lekcji.
1. ZACZYNAMY - WYŚWIETLANIE TEKSTU NA EKRANIE
Pisanie programu w C++ rozpoczynamy (zwykle) od załączania plików
nagłówkowych. Znajdują się w nich definicje funkcji, z których możemy
skorzystać we własnych programach. Więcej na temat plików nagłówkowych
w następnych częściach kursu - zapamiętajmy jedynie, że coś takiego w
ogóle jest.
Trzonem całego programu w C++ jest funkcja main() - to właśnie w
niej znajdują się kolejne instrukcje, które program ma wykonywać.
Instrukcje te znajdują się pomiędzy nawiasami klamrowymi {} (jest to
tzw. ciało funkcji). Napiszmy więc nasz pierwszy program w C++:
#include <iostream.h> // dodawanie pliku nagłówkowego iostream.h
main() // funkcja main() - główna część programu
{ // rozpoczęcie funkcji
cout << "Napis tralalala"; // wyświetlanie napisu - o tym za chwilę
} // koniec funkcji main - koniec programu
Po skompilowaniu i uruchomieniu (patrz: dodatek na końcu tej lekcji) zobaczymy na ekranie coś takiego:
Napis tralalala
Widzimy więc w jaki sposób dodawać pliki nagłówkowe (piszemy
#include - można również używać " " zamiast <>, ale o tym jeszcze
kiedyś przy okazji). W dodanym pliku iostream.h znajdują się funkcje
umożliwiające wykonywanie podstawowych operacji wejścia - wyjścia (ale
tego też nie musimy jeszcze wiedzieć).
Pojawiło się natomiast ważne polecenie cout - służy ono (przede
wszystkim) do wypisywania danych na ekranie (pamiętajmy, że łączy się z
operatorem <<). W C++ ciąg znaków zapisujemy w cudzysłowiu, np.
"znaki". Po dokonaniu odpowiedniej zmiany w programie możemy wyświetlić
na ekranie kilka napisów, np.
cout << "napis1" << "napis2" << endl << "napis3";
Co się jednak dzieje? Po takiej modyfikacji programu na ekranie wyświetla się:
napis1napis2
napis3
Wpisywanie kolejnych ciągów znaków sprawia, że cout łączy je w
jeden. Aby jakoś je "rozdzielić", posłużyliśmy się poleceniem endl
(skrót od: end of line). Umieszczenie go sprawiło, że program
wyświetlił dwa pierwsze napisy razem, trzeci zaś w następnej linijce.
Ten sam efekt możnaby uzyskać stosując przełącznik \n, jednak powoduje
on czasami nieczytelność kodu, dlatego nie będziemy go omawiać.
Należy wspomnieć jeszcze coś o komentarzach. To nic innego, jak
uwagi programisty nt. działania programu (są całkowicie ignorowane
przez kompilator). Można ich używać dwojako: albo przez // (wtedy za
komentarz będzie uznane wszystko od // aż do końca linijki) lub też
przy użyciu /* */ (wszystko, co znajdzie się między gwiazdkami jest
komentarzem).
Nie pisaliśmy o tym wcześniej, ale należy też pamiętać, aby na
końcu każdej instrukcji (oczywiście istnieją wyjątki) umieszczać
średnik. Sygnalizuje on kompilatorowi, że instrukcja się kończy i może
przejść do następnej.
Do zapamiętania z rozdziału:
- pliki nagłówkowe załączamy przy pomocy #include
- podstawowy fundament programu to funkcja main()
- cout odpowiada za wyświetlanie dane na ekranie
- na końcu każdej instrukcji powinien znaleźć się średnik
- komentarz: // - jednolinijkowy lub /* */ - wielolinijkowy
Zadanie:
Napisz program wyświetlający Twoje imię, a trzy linijki niżej Twoje nazwisko (za trudne?) ;-)
2. ZMIENNE, POBIERANIE DANYCH
Umiemy już wyświetlać tekst. Zanim przejdziemy do komunikacji z
użytkownikiem programu, powinniśmy poznać najpierw zmienne. Zmienne to
takie miejsca (w pamięci RAM), gdzie przechowywane są dane. Jak sama
nazwa wskazuje, dane te mogą zmieniać się podczas działania programu.
Każda zmienna posiada swoją nazwę (np. zmienna1) oraz typ (np. int).
Typ zmiennej to po prostu rodzaj danych, jaki moze byc w niej
przechowywany. Jeśli brzmi to zbyt zawile, przeanalizujmy przykład:
mamy zmienną o nazwie zmienna1, w której możemy przechowywać liczby
całkowite (z pewnego zakresu). Nie możemy w tej zmiennej zapisać więc
tekstu (np. "Napis1"), gdyż "Napis1" ma inny typ niż zmienna1. Możemy
zapisać w niej jedynie liczby całkowite (np. 100). Aby korzystać ze
zmiennej, musimy ją najpierw zdefiniować, tzn. powiedzieć
kompilatorowi, jak się będzie nazywać i jakiego będzie typu.
Definicja zmiennej wygląda następująco:
typ_zmiennej nazwa_zmiennej;
Mamy do dyspozycji różne typy danych:
int - liczby całkowite (miejsce w pamięci: 2B, 4B lub więcej)
float - liczby rzeczywiste (miejsce w pamięci: 4B)
double - liczby rzeczywiste o podwójnej precyzji (używane do wyrażania skrajnie małych/dużych liczb)
char - znaki (miejsce w pamięci: 1B)
Dla wymienionych typów danych istnieją różne wariacje (np. unsigned
int), jednak będziemy o nich mówić dopiero, gdy będą nam potrzebne.
Przykład ilustrujący definicję i przypisywanie zmiennym wartości:
float liczba_r; // definicja zmiennej liczba_r...
char znak; // definicja zmiennej znak
liczba_r = 28.25; // wpisanie do zmiennej wartości 28.25
znak = 'a'; // wpisanie do zmiennej znaku 'a'
W programie pojawił się zapis: zmienna = wartość. Powoduje on
zapisanie do zmiennej podanej wartości (prawda, że proste?). (A propos
typu char: należy pamiętać, że o ile ciąg znaków podajemy w
cudzysłowiu, o tyle pojedynczy znak w apostrofach, np. 'a').
Do zmiennej możemy również wpisać zawartość innej zmiennej tego samego typu, np.
int a, b; // mozna definiować zmienne tego samego typu po przecinku
a = 5;
b = a; // dwie zmienne tego samego typu
cout << b; // wartość zmiennych można wyświetlać, ale nie piszemy wtedy " "
Co ciekawe (i pożyteczne), już podczas definicji zmiennych możemy nadawać im wartość, np. int a = 10, b = 5;
No dobrze, ale co z komunikacją z użytkownikiem programu? Otóż
wartości zmiennych można odbierać od użytkownika przy pomocy polecenia:
cin >> nazwa_zmiennej, np:
int liczba, liczba2 = 28;
cin >> liczba; // ważne - bez cudzysłowia!
cout << "Wpisales liczbe: " << liczba << endl << "a ja dodalem: " << liczba2;
Do zapamiętania z rozdziału:
- definicja zmiennej: typ_zmiennej nazwa_zmiennej
- przypisywanie wartości: zmienna = wartosc
- należy pamiętać o zachowywaniu zgodności typów
- instrukcja cin służy do pobierania danych (standardowo z klawiatury)
Zadanie:
Napisz program, który wczyta wiek, wzrost i inicjały użytkownika, a następnie wyświetli je w osobnych linijkach.
3. TROCHĘ MATEMATYKI
Programując, często musimy wykonywać jakieś działania arytmetyczne. Przykładowo dodawanie:
int liczba = 5;
liczba = liczba + 5; // do zmiennej dodajemy 5
Pozostałe operatory arytmetyczne (pomijając poznany operator dodawania: +) to m.in.:
- odejmowanie
* mnożenie
/ dzielenie
Prosty przykład: a = 5*10; // zmianna a jest równa 5*10 = 50
Przy wykonywaniu operacji matematycznych należy pamiętać o
sprawdzeniu typów zmiennych (np. zmienna typu int podzielona przez
zmienną typu int może dać wynik float, więc taki typ zmiennej należy
zdefiniować). Ponieważ jednak ludzie są z reguły leniwi, wymyślono
krótszy zapis:
liczba = liczba + 5 jest równoważny: liczba += 5
Analogicznie postępujemy w przypadku pozostałych działań, np. liczba *= 5;
Przykład:
int a = 5, b = 1;
float wynik;
b *= a; // b jest równe 5 - a*b
wynik = b/2; // wynik jest równy 5/2 = 2.5
cout << wynik;
Do zapamiętania z rozdziału:
- na liczbach i zmiennych można wykonywać działania
- stosowanie zapisów skróconych (np. +=) oszczędza czas i klawiaturę
- wynik może być innego typu niż części składowe działania
Zadanie:
Napisz program, który wczyta 3 liczby i iloczyn 2 pierwszych podzieli przez trzecią, a wynik wyświetli na ekranie.
4. INSTRUKCJA WARUNKOWA IF
Jeśli warunek jest spełniony, wykonaj instrukcję - tak najkrócej
można opisać instrukcję warunkową if. Składnia wygląda następująco: if (warunek) instrukcja;
Do sprawdzania warunku korzystamy z następujących operatorów logicznych:
== równy (nie mylić z przypisaniem =)
!= różny
>= większy lub równy
<= mniejszy lub równy
> większy
< mniejszy
&& iloczyn logiczny (i)
|| suma logiczna (lub)
! negacja logiczna (nie)
Przykładowo:
int liczba;
cin >> liczba;
if (liczba >= 5)
{
cout << "Liczba większa lub równa 5";
cout << "Zgadza się";
}
Warto zwrócić tutaj uwagę na jeszcze jeden aspekt języka C++ -
jeśli chcemy wykonać więcej instrukcji, ale wolelibyśmy potraktować je
jako jedną, umieszczamy je w nawiasie klamrowym { }. Gdyby w naszym
przykładzie nawias ten nie wystąpił, program za każdym razem (bez
względu na wartość logiczną warunku) wyświetlałby napis: "Zgadza się",
gdyż warunek tyczy się wyłącznie instrukcji stojącej bezpośrednio po
nim (po sprawdzeniu warunku program wykonywałby następne instrukcje w
programie, a więc: cout << "Zgadza się"). Nawiasy klamrowe
umożliwiają więc użycie wielu instrukcji w jednym miejscu (tyczy się to
nie tylko konstrukcji if(warunek), ale też wszystkich innych, m.in.
pętli).
W jednej instrukcji warunkowej może znaleźć się również kilka
warunków. Korzystamy wtedy z && lub || (patrz wyżej). Więcej
warunków zapisujemy tak: if((warunek1) && (warunek2)) instrukcje; - jeśli warunek1 i warunek2 są prawdziwe, to wykonaj instrukcje
if((warunek1) || (warunek2)) instrukcje; - jeśli warunek1 lub warunek2 jest prawdziwy, to wykonaj instrukcje
Możemy również skorzystać z negacji:
if(!(warunek1)) instrukcje; - jeśli warunek1 jest fałszywy, to wykonaj instrukcje
A jeśli warunek nie zostanie spełniony? Co wtedy? Jeśli chcemy, aby coś się stało, musimy wówczas posłużyć się instrukcją else:
if(warunek1) instrukcje1; // jeśli warunek jest prawdziwy, to wykonaj instrukcje1
else instrukcje2; // w przeciwnym wypadku wykonaj instrukcje1
Przykład:
char znak;
cin >> znak;
if (znak == 'p') cout << " Nacisnales znak: p";
else cout << "Nacisnales coś innego!";
Oczywiście instrukcje sprawdzania warunku można w sobie zagnieżdżać, np.
if (warunek1) // jeśli warunek1 jest prawdziwy to
if (warunek2) // sprawdź warunek2 i jeśli jest on prawdziwy, to pisz na ekranie:
cout << "Warunki spelnione!";
Przykładzik na zakończenie rozdziału (program liczący pole prostokąta):
#include <iostream.h>
main()
{
int a, b;
cout << "Wprowadz dlugosc pierwszego boku: ";
cin >> a;
cout << endl << "Wprowadz dlugosc drugiego boku: ";
cin >> b;
if ((a != 0) && (b != 0))
cout << endl << "Pole prostokata wynosi: " << a*b;
else cout << "Jako jedna z dlugosci podales 0 - pomylka";
}
Dygresja dla zainteresowanych:
Instrukcja warunkowa sprawdza w istocie jedynie to, czy zdanie
logiczne (warunek) ma wartość logiczną różną od 0. Zatem w przypadku
zapisu: if(20) instrukcja1, instrukcja1 zostałaby wykonana.
Analogicznie - jeśli napisalibyśmy if(0), to warunek nie byłby
spełniony.
Do zapamiętania z rozdziału:
- instrukcja if pozwala na różne zachowania programu w zależności od różnych warunków- składnia: if(warunek)
- nawiasy klamrowe { } umożliwiają wykonanie więcej niż 1 instrukcji
- możliwe (i często stosowane) jest zagnieżdżanie instrukcji, np. jeśli warunek1, to jeśli warunek2, to instrukcja
Zadanie:
Napisz program sprawdzający, czy z podanych odcinków o długościach
podanych przez użytkownika da się zbudować trójkąt (czy suma długości
dwóch boków jest większa od trzeciego), a jeśli tak, to czy jest on
prostokątny (czy dla boków a, b, c: a2 + b2 = c2).
DODATEK O KOMPILATORACH
Kompilator to narzędzie zamieniające kod źródłowy programu (bo tak
nazywa się to, co piszemy) na kod binarny (rozumiany przez komputer).
Najpopularniejszym kompilatorem jest gcc (najczęściej używany do
testowania aplikacji na konkursach i olimpiadach informatycznych). Nic
jednak nie stoi na przeszkodzie, aby korzystać z innych narzędzi, np.
C++ Builder (firmy Borland) albo Dev-C++. Niezwykle przydatną funkcją
kompilatorów jest sprawdzanie błędów. Jeśli takowe wystąpią, są
natychmiast wyświetlane i najczęściej omawiane (proces kompilacji jest
wtedy automatycznie przerywany). Dzięki temu nie musimy się długie
godziny zastanawiać, czy dana funkcja jest poprawna - wystarczy
spróbować skompilować źródło. Jest to nieoceniona pomoc, jeśli chodzi o
sprawdzanie poprawności kodu (nawiasem mówiąc, źródła w C++ zapisuje
się w plikach .cpp).
Jeśli błędy nie wystąpią, kompilator tworzy na dysku plik wykonywalny - jest to już program gotowy do uruchomienia.
Skąd zatem wziąć kompilator? Można znaleźć na CD dołączanych do
czasopism komputerowych, można mieć i o tym nie wiedzieć (np. gcc jest
standardowym pakietem w większości dystrybucji Linuxa), a można też
ściągnąć z Internetu:
gcc:
C++ Builder:
http://www.borland.com/products/downloads/download_cbuilder.html
Dev-C++:
|