Biblioteca
Tutora
BibliotecaInformatică și TIC › clasa a XII-a

Baze de date

Introducerea conceptelor fundamentale privind organizarea, gestionarea și interogarea bazelor de date relaționale.

Bacalaureat

Modelul relațional — tabele, chei, integritate

O bază de date relațională organizează datele în tabele (relații). Fiecare tabel are coloane (câmpuri, atribute) — cu nume și tip de date fixe — și linii (înregistrări, tupluri) — câte una pentru fiecare entitate memorată. Software-ul care creează și administrează baza este SGBD-ul (sistem de gestiune a bazelor de date): MySQL, PostgreSQL, Oracle, SQLite. Distincția SGBD vs baza de date propriu-zisă este întrebare de teorie: baza este colecția de date, SGBD-ul este programul care o gestionează.

Cheia primară (primary key) este câmpul sau grupul de câmpuri care identifică unic fiecare înregistrare. Regulile ei: valorile sunt unice și nu pot fi NULL. Un tabel poate avea mai multe câmpuri candidate la acest rol (chei candidate), dar o singură cheie primară.

Cheia externă (foreign key) este un câmp dintr-un tabel care referă cheia primară a altui tabel, materializând legătura dintre ele. Ea impune integritatea referențială: nu poți insera o valoare care nu există în tabelul referit și nu poți șterge o înregistrare părinte cât timp există înregistrări copil care o referă (fără reguli speciale de tip cascadă).

Tipurile de relații între tabele:

Definirea structurii: SQL DDL

SQL (Structured Query Language) are două familii de comenzi care se cer deosebite la examen: DDL (Data Definition Language) — definește structura — și DML (Data Manipulation Language) — lucrează cu datele.

Comenzile DDL esențiale:

Perechea de comenzi confundată cel mai des la grile: DROP vs DELETE vs TRUNCATE. DELETE (DML) șterge înregistrări, păstrând tabelul; TRUNCATE golește rapid toate înregistrările, păstrând structura; DROP șterge tabelul însuși. Cine răspunde că DELETE fără WHERE șterge tabelul pierde punctul — tabelul rămâne, doar gol.

Exemplu de structură pentru o școală:

Alegerea tipului de date se punctează: numerele pe care se fac calcule se țin ca tipuri numerice, nu ca text; datele calendaristice ca DATE, nu VARCHAR — altfel compararea și sortarea cronologică nu mai funcționează corect. VARCHAR(n) reține șiruri de lungime variabilă cu maximum n caractere, spre deosebire de CHAR(n), care ocupă mereu exact n.

Interogarea datelor: SELECT, WHERE, ORDER BY

Interogarea fundamentală are forma: SELECT coloane FROM tabel WHERE condiție ORDER BY criteriu. SELECT alege coloanele (proiecție), WHERE filtrează liniile (selecție) — inversarea celor două roluri este o greșeală de teorie frecventă.

Ordinea sintactică a clauzelor este fixă: SELECT, FROM, WHERE, GROUP BY, HAVING, ORDER BY. Scrierea lui WHERE după ORDER BY este eroare de sintaxă.

Exemplu integrat: elevii din clasa a XII-a A cu media peste 9, în ordine alfabetică — SELECT nume FROM elevi WHERE clasa = „12A” AND media > 9 ORDER BY nume;

Funcții agregate, GROUP BY și JOIN

Funcțiile agregate calculează o valoare unică dintr-o mulțime de linii: COUNT (numărare), SUM (sumă), AVG (medie), MIN, MAX. Nuanță de punctaj: COUNT(*) numără toate liniile, în timp ce COUNT(coloana) numără doar liniile în care coloana nu este NULL.

GROUP BY împarte liniile în grupuri după valorile unei coloane, iar funcțiile agregate se calculează pe fiecare grup: SELECT clasa, AVG(media) FROM elevi GROUP BY clasa — media fiecărei clase. Regula strictă: în SELECT pot apărea doar coloanele de grupare și funcții agregate; a cere o coloană negrupată și neagregată este eroare (ce nume de elev ai afișa pentru un grup întreg?).

Distincția WHERE vs HAVING este întrebarea preferată a subiectelor: WHERE filtrează liniile înainte de grupare și nu poate conține funcții agregate; HAVING filtrează grupurile după calcularea agregatelor. „Clasele cu media peste 8”: GROUP BY clasa HAVING AVG(media) > 8 — cu WHERE nu se poate exprima.

JOIN combină linii din două tabele pe baza unei condiții de legătură, tipic cheie externă = cheie primară:

Exemplu: SELECT e.nume, n.nota FROM elevi e INNER JOIN note n ON e.id = n.id_elev; — fiecare notă alături de numele elevului. Fără condiția ON se obține produsul cartezian: fiecare linie cu fiecare linie, rezultat umflat și fără sens — bug clasic la subiectele practice.

Actualizarea datelor și normalizarea

Comenzile DML de modificare:

Avertismentul care se cere explicit: UPDATE sau DELETE fără clauza WHERE se aplică TUTUROR înregistrărilor din tabel. Un UPDATE elevi SET media = 10 fără WHERE rescrie media tuturor — greșeala este ireversibilă fără copie de siguranță.

Normalizarea este procesul de organizare a tabelelor astfel încât să se elimine redundanța (aceeași informație memorată de mai multe ori) și anomaliile de actualizare, inserare și ștergere. Formele normale, la nivelul cerut:

Intuiția de reținut: normalizarea sparge tabelele mari în tabele mai mici legate prin chei externe, astfel încât fiecare fapt să fie memorat o singură dată.

De reținut

bază de date relațională
colecție de date organizate în tabele formate din coloane (atribute cu tip fixat) și linii (înregistrări), legate între ele prin chei
SGBD
sistem de gestiune a bazelor de date — programul care creează, administrează și interoghează bazele de date (exemple: MySQL, PostgreSQL, Oracle)
cheie primară
câmp sau grup de câmpuri care identifică unic fiecare înregistrare a unui tabel; valorile sale sunt unice și nu pot fi NULL
cheie externă
câmp al unui tabel care referă cheia primară a altui tabel, realizând legătura dintre tabele și asigurând integritatea referențială
SELECT
comanda SQL de interogare, cu forma generală SELECT coloane FROM tabel WHERE condiție ORDER BY criteriu; SELECT alege coloanele, WHERE filtrează liniile
funcții agregate
funcții SQL care calculează o valoare unică dintr-o mulțime de linii: COUNT, SUM, AVG, MIN, MAX; COUNT(*) numără toate liniile, COUNT(coloana) doar pe cele cu valoare nenulă
GROUP BY / HAVING
GROUP BY grupează liniile după valorile unei coloane pentru calcule agregate pe grup; HAVING filtrează grupurile după valorile agregatelor, spre deosebire de WHERE, care filtrează liniile înainte de grupare
INNER JOIN / LEFT JOIN
INNER JOIN combină liniile din două tabele păstrând doar perechile cu corespondent în ambele; LEFT JOIN păstrează toate liniile tabelului stâng, completând cu NULL acolo unde lipsește corespondentul
normalizare
procesul de reorganizare a tabelelor pentru eliminarea redundanței și a anomaliilor de actualizare, prin descompunerea în tabele legate prin chei externe (formele normale FN1, FN2, FN3)
NULL
marcaj pentru valoare necunoscută sau absentă într-un câmp; se testează exclusiv cu IS NULL sau IS NOT NULL, orice comparație directă cu NULL nefiind adevărată

Greșeli frecvente

Greșit: Testarea valorilor lipsă cu condiția camp = NULL
Corect: NULL nu este egal cu nimic, nici cu el însuși; valorile lipsă se testează cu camp IS NULL, respectiv camp IS NOT NULL
Greșit: Folosirea clauzei WHERE pentru condiții pe funcții agregate, de tip WHERE AVG(nota) > 8
Corect: WHERE filtrează liniile înainte de grupare și nu poate conține agregate; condițiile pe rezultatele agregatelor se pun în HAVING, după GROUP BY
Greșit: Rularea comenzilor UPDATE sau DELETE fără clauza WHERE
Corect: Fără WHERE, comanda se aplică tuturor înregistrărilor din tabel — toate liniile sunt modificate sau șterse; condiția WHERE delimitează exact înregistrările vizate
Greșit: Confundarea comenzii DELETE cu DROP TABLE
Corect: DELETE șterge înregistrări și păstrează tabelul (chiar dacă rămâne gol); DROP TABLE elimină tabelul cu totul, inclusiv structura lui
Greșit: Implementarea unei relații m:n printr-o cheie externă directă între cele două tabele
Corect: Relația m:n cere un tabel asociativ intermediar, cu două chei externe către cele două tabele; o singură cheie externă poate exprima doar relații 1:n

Test — 6 întrebări ca la examen

1. Care afirmație despre cheia primară a unui tabel este adevărată?
  1. poate conține valori duplicate dacă sunt pe linii diferite
  2. identifică unic fiecare înregistrare și nu poate fi NULL
  3. este obligatoriu de tip numeric
  4. un tabel poate avea oricâte chei primare
Vezi răspunsul
identifică unic fiecare înregistrare și nu poate fi NULL. Cheia primară garantează identificarea unică a fiecărei linii, deci exclude duplicatele și valorile NULL. Poate fi și de tip text (de exemplu CNP memorat ca șir), iar un tabel are o singură cheie primară — celelalte câmpuri unice rămân chei candidate.
2. Interogarea SELECT nume FROM elevi WHERE nume LIKE „_a%” returnează elevii al căror nume:
  1. începe cu litera a
  2. conține litera a pe orice poziție
  3. are litera a pe a doua poziție
  4. se termină cu litera a
Vezi răspunsul
are litera a pe a doua poziție. Liniuța de subliniere ține locul exact unui caracter, deci prima literă e oarecare, a doua trebuie să fie a, iar procentul acoperă restul. Varianta „începe cu a” corespunde șablonului „a%” — confuzia dintre cele două metacaractere este exact ce testează întrebarea.
3. Pentru a afișa clasele în care media notelor depășește 8, interogarea corectă este:
  1. SELECT clasa FROM elevi WHERE AVG(media) > 8 GROUP BY clasa
  2. SELECT clasa FROM elevi GROUP BY clasa HAVING AVG(media) > 8
  3. SELECT clasa FROM elevi HAVING AVG(media) > 8
  4. SELECT clasa, AVG(media) FROM elevi WHERE media > 8
Vezi răspunsul
SELECT clasa FROM elevi GROUP BY clasa HAVING AVG(media) > 8. Condiția poartă asupra unei valori agregate pe grup, deci cere GROUP BY urmat de HAVING. Prima variantă — distractorul principal — pune agregatul în WHERE, ceea ce este interzis, WHERE evaluându-se pe linii individuale, înainte de formarea grupurilor; ultima filtrează elevii cu media personală peste 8, altă întrebare decât cea pusă.
4. Tabelele elevi și note sunt legate prin note.id_elev = elevi.id. Pentru a afișa TOȚI elevii, inclusiv pe cei fără nicio notă, se folosește:
  1. INNER JOIN între elevi și note
  2. LEFT JOIN cu tabelul elevi în stânga
  3. două interogări SELECT concatenate
  4. produsul cartezian al celor două tabele
Vezi răspunsul
LEFT JOIN cu tabelul elevi în stânga. LEFT JOIN păstrează toate liniile tabelului din stânga (elevi), completând cu NULL coloanele notelor pentru elevii fără corespondent. INNER JOIN — alegerea reflexă a multora — elimină exact elevii fără note, adică pe cei ceruți explicit de enunț.
5. Ce efect are comanda DELETE FROM elevi; executată fără clauza WHERE?
  1. șterge tabelul elevi împreună cu structura lui
  2. șterge toate înregistrările din tabel, dar tabelul rămâne
  3. produce eroare de sintaxă, WHERE fiind obligatoriu
  4. șterge doar prima înregistrare din tabel
Vezi răspunsul
șterge toate înregistrările din tabel, dar tabelul rămâne. DELETE fără WHERE se aplică tuturor liniilor, dar structura tabelului rămâne intactă — tabelul devine gol, nu inexistent. Prima variantă descrie DROP TABLE, confuzia clasică între ștergerea datelor și ștergerea obiectului.
6. Într-un tabel cu elevii unei școli se memorează pe fiecare linie și numele dirigintelui, care depinde doar de clasa elevului. Această structură încalcă:
  1. forma normală 1, pentru că valorile nu sunt atomice
  2. forma normală 3, existând o dependență tranzitivă prin câmpul clasa
  3. integritatea referențială
  4. unicitatea cheii primare
Vezi răspunsul
forma normală 3, existând o dependență tranzitivă prin câmpul clasa. Dirigintele depinde de clasă, iar clasa de elev — o dependență tranzitivă între câmpuri nechie, exact ce interzice FN3; consecința practică este redundanța: numele dirigintelui se repetă la fiecare elev al clasei. FN1 nu e încălcată, valorile fiind atomice — distractorul mizează pe faptul că FN1 e singura formă normală pe care mulți o rețin.
Deschide varianta interactivă — cu AI care îți explică
← Structuri de date avansateProiectarea algoritmilor – complexitate →
BiologieChimieEconomieFilosofieFizicăGeografieInformatică și TICIstorieLogică și argumentareMatematicăPsihologieLimba și literatura română