Alapok, Változók és Konzolos I/O
Részletes elméleti bemutató a PySuli struktúrája és az NJE Programozás I. 1. heti előadásának megfelelően: adattípusok, konzolos beolvasás/kiírás, zárthelyi követelmények és az 1. hét összes órai példaprogramja.
A lecke felépítése:
1. Változók, Memória és Alapvető Adattípusok
A C++ egy statikusan és erősen típusos fordítóprogramos nyelv. Ez azt jelenti, hogy minden változónak még a fordítás pillanatában pontosan ismertnek kell lennie a típusának és méretének. Amikor deklarálsz egy változót, a fordító lefoglalja a megfelelő méretű rekeszt a számítógép memóriájában (RAM).
C++ elemi adattípusok mérete és értékkészlete:
| Adattípus | Méret (bájt) | Értékkészlet (Signed) | Értékkészlet (Unsigned) | Megjegyzés |
|---|---|---|---|---|
bool | 1 bájt | false (0), true (1) | - | Logikai feltételek és állapotok |
char | 1 bájt | -128 ... +127 | 0 ... 255 | ASCII karakterek tárolása |
short int | 2 bájt | -32 768 ... +32 767 | 0 ... 65 535 | Rövid egész számok |
int | 4 bájt | -2 147 483 648 ... +2 147 483 647 | 0 ... 4 294 967 295 | Alapértelmezett egész típus |
float | 4 bájt | ±1.2·10⁻³⁸ ... ±3.4·10³⁸ | - | Lebegőpontos szám (~7 tizedes pontosság) |
double | 8 bájt | ±2.2·10⁻³⁰⁸ ... ±1.8·10³⁰⁸ | - | Dupla pontosságú valós szám (~15-17 tizedes) |
3.14 vagy (float)r), különben a C++ egészosztást (csonkítást) hajt végre!
Működő C++ mintakód:
// Változók deklarálása és inicializálása C++-ban
#include <iostream>
#include <string>
using namespace std;
int main() {
int eletkor = 20; // Egész szám (4 bájt)
double atlag = 4.75; // Lebegőpontos szám (dupla pontosság)
char osztalyzatBetu = 'A'; // Egyetlen karakter (aposztróf!)
bool sikeresVizsga = true; // Logikai érték (true / false)
string nev = "Kovacs Peter"; // Szöveges lánc (idézőjel!)
cout << "Nev: " << nev << " (" << eletkor << " eves)" << endl;
cout << "Tanulmanyi atlag: " << atlag << endl;
cout << "Vizsgaeredmeny: " << (sikeresVizsga ? "Sikeres" : "Sikertelen") << endl;
return 0;
} 2. Adatfolyamok: Konzolos Beolvasás (cin) és Kiírás (cout)
A C++ nem beépített függvényekkel, hanem adatfolyamokkal (stream) dolgozik. Az iostream könyvtár két legfontosabb objektuma:
cout(Character Output): A szabványos kimeneti adatfolyam, a konzolképernyő. Összekapcsoló operátora a<<(beszúrás).cin(Character Input): A szabványos bemeneti adatfolyam, a billentyűzet. Összekapcsoló operátora a>>(kivonás / kinyerés).
A cin és a getline közötti alapvető különbség:
A cin >> valtozo; utasítás a szóközöknél, tabulátoroknál és újsoroknál (whitespace) automatikusan megáll! Ha egy teljes nevet vagy mondatot szeretnél beolvasni, ami szóközöket tartalmaz, a getline(cin, valtozo); függvényt kell használnod.
cin >> szam; után hívsz getline(cin, szoveg);-et, a getline azonnal üres sort olvas! Ennek oka, hogy a szám után leütött Enter (újsor karakter, \n) a billentyűzet pufferében marad. Megoldás: cin.ignore(); hívása a getline előtt!
// Konzolos adatbekérés és képernyőre írás részletesen
#include <iostream>
#include <string>
using namespace std;
int main() {
// 1. cout és << (Stream insertion / Beszúrás operátor)
cout << "Udvozollek a C++ vilagaban!" << endl;
// 2. cin és >> (Stream extraction / Kivonás operátor)
int szam1, szam2;
cout << "Adj meg ket egesz szamot (szokozzel elvalasztva): ";
cin >> szam1 >> szam2; // Egyszerre több változóba olvasunk
cout << "A beolvasott szamok: " << szam1 << " es " << szam2 << endl;
cout << "Osszeguk: " << szam1 + szam2 << endl;
// 3. Puffer ürítés cin után, mielőtt getline-t hívnánk!
cin.ignore();
// 4. Teljes szövegsor beolvasása szóközzel: getline()
string kedvencTantargy;
cout << "Mi a kedvenc egyetemi tantargyad? ";
getline(cin, kedvencTantargy);
cout << "Remek valasztas: " << kedvencTantargy << "!" << endl;
return 0;
} 3. Típuskonverzió és az ASCII Karakterkódolás
A számítógép a betűket valójában bináris számokként tárolja az ASCII (American Standard Code for Information Interchange) kódrendszer szerint. Ez azt jelenti, hogy a C++-ban a char és az int típusok között közvetlen átjárás van.
Legfontosabb ASCII kódok, amiket fejből illik tudni:
'0'értéke: 48 (és'9'értéke: 57)'A'értéke: 65 (nagybetűk kezdete)'a'értéke: 97 (kisbetűk kezdete, a távolság pontosan 32!)- Szóköz értéke: 32, Enter (újsor): 10
// Karakterek memóriareprezentációja és típuskonverzió
#include <iostream>
using namespace std;
int main() {
char betu = 'A';
// Implicit konverzió (char -> int)
int asciiKod = betu;
cout << "A '" << betu << "' karakter ASCII kodja: " << asciiKod << endl;
// Eltolásos műveletek: Kisbetűvé alakítás
// Mivel az angol ábécében a távolság fix ('a' - 'A' = 32):
char kisbetu = betu + 32;
cout << "Kisbetus parja: " << kisbetu << " (kodja: " << int(kisbetu) << ")" << endl;
// Karakterből számjegyérték kinyerése:
char szamjegyChar = '7';
int valodiErtek = szamjegyChar - '0'; // '7' - '0' = 55 - 48 = 7
cout << "A karakter valodi szamerteke: " << valodiErtek << endl;
return 0;
} 4. Formázott Kiíratás: iomanip vs printf
A programozási feladatoknál gyakori követelmény, hogy a lebegőpontos számokat fix tizedesjegy-pontossággal jelenítsük meg (például pénznél 2 tizedesjegy). C++-ban erre két bevett módszer létezik:
- A modern C++ módszer:
#include <iomanip>és acout << fixed << setprecision(2) << szam;manipulátorok. - A C nyelvből örökölt klasszikus:
#include <cstdio>és aprintf("%.2f", szam);hívás.
// Formázott kiíratás: C++ iomanip vs klasszikus printf
#include <iostream>
#include <iomanip>
#include <cstdio>
using namespace std;
int main() {
double pi = 3.14159265359;
// 1. Megoldás: C++ standard iomanip könyvtár
cout << "Alapertek: " << pi << endl;
cout << "2 tizedesre kerekitve (setprecision): "
<< fixed << setprecision(2) << pi << endl;
// 2. Megoldás: Klasszikus C stílusú printf
printf("printf segitsegevel (%%.2f): %.2f\n", pi);
return 0;
} Az alábbiakban a Neumann János Egyetem Programozás I. 1. heti előadásán és gyakorlatán szereplő hivatalos feladatok (2.pelda – 9.pelda) forráskódjai és magyarázatai találhatók.
2. Példa: Négyzet Kerülete és Értékadás
Egyszerű egész típusú (int) változó deklarálása, értékadás (hossz = 15;), valamint a kerület képletének (4 * hossz) közvetlen kiíratása az adatfolyamba.
// 1. Hét / 2. példa - Négyzet kerülete
#include <iostream>
using namespace std;
int main()
{
int hossz;
hossz = 15;
cout << "A negyzet kerulete:";
cout << 4 * hossz << "cm" << endl;
// Rövidebben: cout << "A negyzet kerulete: " << 4 * hossz << "cm\n";
return 0;
} 3. Példa: Aritmetikai Operátorok & Maradékképzés (%)
Az alapműveletek C++-ban: összeadás (+), kivonás (-), szorzás (*), egészosztás (/), és a kiemelten fontos maradékképzés operátor (%), amely nélkülözhetetlen a párosság- és oszthatósági vizsgálatokhoz.
// 1. Hét / 3. példa - Aritmetikai műveletek és egészosztás
#include <iostream>
using namespace std;
int main()
{
int a = 8, b = 4;
cout << "a + b: " << a + b << endl; // 12 (Összeadás)
cout << "a - b: " << a - b << endl; // 4 (Kivonás)
cout << "a * b: " << a * b << endl; // 32 (Szorzás)
cout << "a / b: " << a / b << endl; // 2 (Egészosztás)
cout << "a % b: " << a % b << endl; // 0 (Maradékképzés / Modulo)
return 0;
} 4. & 6. Példa: Kör Kerület, Terület & Explicit Típuskonverzió
A 4. példa szemlélteti, mi történik, ha int típusú változóba mentjük a lebegőpontos szorzatot: a C++ levágja a tizedeseket (csonkolás).
A 6. példa a helyes megoldást mutatja: nem tárolunk felesleges segédváltozót, hanem az explicit (float) típuskényszerítéssel közvetlenül a kimeneten jelenítjük meg a tizedeseket.
4.pelda-kor.cpp (int csonkolással):
// 1. Hét / 4. példa - Kör kerület és terület (int csonkolási teszt)
#include <iostream>
using namespace std;
int main()
{
// r deklarálása és inicializálása, k és t változók definiálása
int r = 15, k, t;
k = 2 * r * 3.14;
t = r * r * 3.14;
cout << "Az " << r << "cm sugaru kor kerulete: " << k << "cm, terulete pedig: " << t << "cm2" << endl;
// Megjegyzés: a kiíratásnál nem jelenik meg tizedes rész, mert az int típus miatt csonkolja!
return 0;
} 6.pelda-kor.cpp (float típuskényszerítéssel):
// 1. Hét / 6. példa - Kör kerület/terület változó nélküli lebegőpontos típuskényszerítéssel
#include <iostream>
using namespace std;
int main()
{
int r = 8;
// Explicit (float) típuskonverzió a pontos tizedesjegyek megőrzéséhez
cout << "A kor kerulete: " << (float)(2 * r * 3.14) << "cm\n";
cout << "A kor terulete: " << (float)(r * r * 3.14) << "cm2" << endl;
return 0;
} 5. Példa: Karakter Megjelenítése Számként (ASCII kód)
Egy char betu = 'z'; változó közvetlen értékadása egész típusú (int) változónak. A kiíratás bizonyítja, hogy a karakter mögött a 122-es ASCII kód tárolódik.
// 1. Hét / 5. példa - Betű és ASCII numerikus kód
#include <iostream>
using namespace std;
int main()
{
int i;
char betu = 'z'; // Karakter megadása szimpla idézőjelek ('') között
i = betu; // Az int típusú i változó értéke az adott betű ASCII kódja lesz (122)
cout << "A betu szamkent: " << i << ", karakterkent: " << betu << endl;
return 0;
} 7. Példa: Téglalap Oldalainak Bekérése és Számítása
Két változó egyidejű bekérése egyetlen cin >> a >> b; utasítással, majd a kerület (2 * (a + b)) és terület (a * b) kiszámítása.
// 1. Hét / 7. példa - Téglalap kerület és terület konzolos beolvasással
#include <iostream>
using namespace std;
int main()
{
int a, b;
cout << "Adja meg a teglalap oldalainak hosszat: \n";
cin >> a >> b;
cout << "A teglalap kerulete: " << 2 * (a + b) << "cm" << endl;
cout << "A teglalap terulete: " << a * b << "cm2" << endl;
return 0;
} 8. Példa: Valutaváltó (Lebegőpontos Szorzás)
Konzolos euró kalkulátor: tizedesponttal megadott euró árfolyam (double arfolyam) és az átváltandó összeg bekérése, majd a forint összeg kiszámítása.
// 1. Hét / 8. példa - Valutaváltó kalkulátor
#include <iostream>
using namespace std;
int main()
{
double arfolyam;
double euro;
int forint;
cout << "Kerem az aktualis euro arfolyamot (pl.: 410.5): ";
cin >> arfolyam;
cout << "Hany eurot szeretne atvaltani?: ";
cin >> euro;
forint = euro * arfolyam;
cout << "\n--- Valutavalto ---" << endl;
cout << euro << " EUR erteke: " << forint << " HUF." << endl;
return 0;
} 9. Példa: Másodpercek Felbontása Órára, Percre és Másodpercre
Tipikus egyetemi zárthelyi és vizsgafeladat: másodpercek átváltása ora = ido / 3600; egészosztással és mp = ido % 3600; maradékképzéssel.
// 1. Hét / 9. példa - Idő másodpercekből óra, perc és mp felbontásra
#include <iostream>
using namespace std;
int main()
{
int ido, ora, perc, mp;
cout << "Adja meg az idot masodpercekben: ";
cin >> ido;
ora = ido / 3600; // 1 óra = 3600 másodperc
mp = ido % 3600; // A megmaradt másodpercek az órák levonása után
perc = mp / 60; // A fennmaradó másodpercekből hány egész perc jön ki
mp = mp % 60; // A legvégén megmaradt tiszta másodpercek
cout << "A megadott ido: ";
cout << ora << " ora, " << perc << " perc es " << mp << " masodperc." << endl;
return 0;
}