This is an old revision of the document!


Tema 2 – Simulare Fermă (C++)

🌾 Simulare Fermă - Maximizare Profit 🚜

Gestionează o fermă virtuală și maximizează profitul prin plantare strategică și rotație culturilor!

📅 Publicare: 02.11.2024
Deadline: 16.11.2024, ora 23:59
🎯 Punctaj Total: 10p (9p teste + 1p README + până la 5p bonus clasament)
🏆 Clasament Live: rezultate.eu
📝 Accept Assignment: Classroom Link

Autor: Trifu Marius-Constantin

Informații Generale

Tehnologii:

  • ✅ Limbaj: C++ (fără STL)
  • ✅ Testare: 18 teste automate
  • ✅ Deploy: GitHub Actions
  • ✅ Clasament: rezultate.eu

Cerințe:

  • NU folosiți STL
  • ✅ Implementare OOP
  • ✅ Organizare: fișiere .h / .cpp
  • ✅ Compilare cu make

1. Descriere

Simulați gestionarea unei ferme pe mai multe zile. Scopul este să maximizați suma finală de bani prin plantarea și vânzarea legumelor, respectând reguli de rotație a culturilor și constrângeri financiare.

🎯 Obiectiv: Maximizează SUMA_FINALA = bani_inițiali + venituri - cheltuieli

Reguli Importante

🚫 Rotație Culturi Identice:

În același pătrat NU poți planta două culturi identice una după alta.

Exemplu: Dacă în pătratul 00×00 ai plantat morcov la ziua 1 și l-ai cules la ziua 4, nu poți planta din nou morcov în același pătrat imediat după.

Regula: Trebuie să aștepți cel puțin 3 zile de la culegere.

✅ Plante Prietenoase:

Unele legume pot fi plantate doar după alte legume specifice.

Exemplu:

  • Morcov → poate fi plantat doar după ceapă
  • Ceapă → poate fi plantată după orice (N/A)

Aceste relații sunt definite în secțiunea ROTATIE.

💰 Constrângeri Financiare:

  • Ai o sumă inițială de bani
  • Fiecare plantare costă bani
  • NU poți planta dacă nu ai bani suficienți
  • Câștigi bani la culegere (vinzi leguma)

2. Formate Fișiere

📝 Atenție la format! Respectați exact structura specificată.

2.1 Fișier de Intrare: ferma.txt

Format general:

ferma.txt
L L ZILE BANI N
nume_leguma1 timp_cultivare1 cost1 pret_vanzare1
nume_leguma2 timp_cultivare2 cost2 pret_vanzare2
...
ROTATIE M
leguma1 N/A
leguma2 leguma1
leguma3 leguma2
leguma4 leguma1
...

Explicații câmpuri:

  • L – dimensiunea fermei (L × L pătrate), 1 ≤ L ≤ 99
  • ZILE – numărul de zile de simulare, 1 ≤ ZILE ≤ 100
  • BANI – suma inițială de bani (RON), 1 ≤ BANI ≤ 10000
  • N – numărul de legume definite, 1 ≤ N ≤ 20
  • nume_leguma – numele legumei (maxim 30 caractere, fără spații)
  • timp_cultivare – numărul de zile necesare pentru cultivare, 1 ≤ timp_cultivare ≤ 30
  • cost – costul de plantare a unei legume (RON), 1 ≤ cost ≤ 1000
  • pret_vanzare – prețul de vânzare pentru o legumă (RON), 1 ≤ pret_vanzare ≤ 5000
  • ROTATIE M – secțiunea ce definește relațiile de rotație între legume
  • M – numărul de linii de rotație, M ≥ N
  • leguma1 leguma2 – leguma1 poate fi plantată după leguma2
  • leguma1 N/A – leguma1 nu are restricții de rotație (poate fi plantată după orice legumă)
  • Pot exista mai multe linii pentru aceeași legumă (leguma1 poate fi plantată după leguma2, leguma3, etc.)

Restricții:

  • Numărul total de tipuri de legume: 1 ≤ N ≤ 20
  • Fiecare legumă apare cel mult o dată în lista de legume
  • Numărul de linii de rotație: M ≥ N (pot fi mai multe reguli pentru aceeași legumă)
ferma.txt
3 3 10 500 4
morcov 3 50 200
ceapa 2 30 150
castravete 4 80 300
roșie 5 100 400
ROTATIE 4
morcov ceapa
ceapa N/A
castravete N/A
roșie morcov

Interpretare exemplu:

  • Fermă 3×3 (9 pătrate disponibile, coordonate de la 00×00 până la 02×02)
  • Simulare 10 zile
  • 500 RON inițiali
  • 4 tipuri de legume: morcov (3 zile, cost 50, preț 200), ceapă (2 zile, cost 30, preț 150), etc.
  • Rotație: morcov poate fi plantat după ceapă; ceapa/castravete poate fi plantat după orice (N/A); roșie poate fi plantat după morcov

2.2 Fișier de ieșire: ferma.out

Format general:

ferma.out
ZI ACTIUNE PATRAT LEGUMA
ZI ACTIUNE PATRAT LEGUMA
...
SUMA_FINALA: suma

Tipuri de acțiuni:

  • planteaza – plantarea unei legume într-un pătrat liber sau eliberat
  • culege – culegerea unei legume mature (după ce timpul de cultivare a trecut) și vânzarea acesteia

Format linie acțiune:

  • `ZI ACTIUNE PATRAT [LEGUMA]`
  • ZI – ziua în care se face acțiunea (1 ≤ ZI ≤ ZILE)
  • ACTIUNE – `planteaza` sau `culege`
  • PATRAT – ID-ul pătratului sub formă de coordonată `linia_coloana` (ex: `00×00`, `01×02`)
  • LEGUMA – numele legumei (doar pentru acțiunea `planteaza`)

Reguli de numerotare pătrate:

  • Pătratele sunt identificate prin coordonate matrice (linie, coloană)
  • Coordonatele sunt de la 0 la L-1 pentru linie și coloană
  • Format: `liniaxcoloana` cu două cifre fiecare (ex: `00×00`, `00×01`, …, `01×00`, `01×01`, …, `99×99`)
  • Exemplu pentru fermă 3×3:
    • Linia 0: `00×00`, `00×01`, `00×02`
    • Linia 1: `01×00`, `01×01`, `01×02`
    • Linia 2: `02×00`, `02×01`, `02×02`
ferma.out
1 planteaza 00x00 ceapa
1 planteaza 00x01 ceapa
3 culege 00x00
3 culege 00x01
4 planteaza 00x00 morcov
4 planteaza 00x01 morcov
7 culege 00x00
7 culege 00x01
SUMA_FINALA: 740

Explicație exemplu:

  • Zi 1: Plantăm 2 cepe (pătrate 00×00, 00×01) - Cost: 2×30 = 60 RON
  • Zi 3: Culegem cele 2 cepe (mature după 2 zile) - Venit: 2×150 = 300 RON
  • Zi 4: Replantăm morcovi în pătratele 00×00 și 00×01 (după ceapă, conform ROTATIE) - Cost: 2×50 = 100 RON
  • Zi 7: Culegem morcovi (maturi după 3 zile) - Venit: 2×200 = 400 RON
  • Suma finală: 500 (inițial) + 700 (venituri) - 160 (cheltuieli) = 1040 RON

Observații:

  • Acțiunile trebuie să fie valide: nu poți planta dacă nu ai bani sau dacă pătratul este ocupat.
  • Nu poți culege o legumă care nu este matură sau care nu există.
  • Verificați regulile de validare pentru detalii despre rotație.

3. Reguli de Validare

Programul vostru trebuie să respecte următoarele constrângeri. Scriptul de verificare verifică automat fiecare regulă!

🔄 Regula 1: Rotație Culturi Identice

❌ Nu poți planta aceeași legumă imediat după culegere!

Situație Zi Culegere Când poți replanta aceeași legumă?
Culegi morcov din 00×00 Ziua 4 Ziua 8 sau mai târziu (după 3 zile)
Culegi ceapă din 01×01 Ziua 10 Ziua 14 sau mai târziu

Regulă: Dacă culegi leguma X din pătratul P la ziua Z, NU poți planta X în P în zilele Z, Z+1, Z+2.

Poți planta: altă legumă (dacă respectă ROTATIE) sau aceeași legumă după minim 3 zile.

🌱 Regula 2: Rotație Legume Prietenoase

✅ Respectă relațiile din secțiunea ROTATIE!

Exemplu:

ROTATIE 2
morcov ceapa    ← Morcov poate fi plantat doar după ceapă
ceapa N/A       ← Ceapă poate fi plantată după orice
Pătrat Legumă Culeasă Ce poți planta după?
00×00 ceapă (zi 3) morcov (zi 4+) sau ceapă (zi 7+, după 3 zile)
00×01 morcov (zi 7) Nimic altceva! (morcov doar după ceapă)

Reguli:

  • Dacă leguma are N/A → poate fi plantată după orice legumă
  • Dacă leguma are restricții (ex: morcov ceapa) → poate fi plantată doar după legumele specificate
  • Trebuie să treacă cel puțin 1 zi de la culegere înainte de replantare

Atenție la pătratele noi! Într-un pătrat care nu a fost plantat niciodată, poți planta doar legume cu N/A în ROTATIE!

📦 Regula 3: Disponibilitate Pătrat

Când e un pătrat LIBER pentru plantare?

Status Pătrat Condiții
🆕 Niciodată folosit Poți planta doar legume cu N/A în ROTATIE
După culegere A trecut ≥1 zi + respectă rotația (regula 2) + respectă 3 zile pentru aceeași legumă (regula 1)
Ocupat Așteaptă până la culegere!

💰 Regula 4: Gestionare Bani

Formula sumei finale:

SUMA_FINALA = BANI_INIȚIALI + VENITURI - CHELTUIELI

Unde:
  VENITURI = Σ (preț_vânzare pentru fiecare legumă culeasă)
  CHELTUIELI = Σ (cost pentru fiecare legumă plantată)

Constrângeri:

  • NU poți planta dacă bani_curent < cost_legumă
  • ✅ Banii cresc la fiecare culegere
  • ✅ Banii scad la fiecare plantare

⏰ Regula 5: Maturitate Legume

Când poți culege o legumă?

Legumă Timp Cultivare Plantată Ziua Gata de Cules Ziua
Ceapă 2 zile 1 3 (1 + 2)
Morcov 3 zile 4 7 (4 + 3)
Roșie 5 zile 1 6 (1 + 5)

Regulă: zi_culegere ≥ zi_plantare + timp_cultivare

Sfat: NU planta legume care nu ajung la maturitate înainte de finalul simulării!

4. Implementare

  • În main.cpp trebuie să existe doar `int main(int argc, char* argv[])`, unde apelați funcții.
  • Evitați declararea variabilelor direct în `main`.
  • Toate funcțiile trebuie documentate cu un scurt comentariu.
  • Folosiți `<fstream>` și verificați deschiderea fișierelor.
  • Separator zecimal: punct (`.`).
  • Gestionați starea fermei (ce este plantat în fiecare pătrat, când a fost plantat, etc.).

Argumente linie de comandă:

  • Programul acceptă 2 argumente:
    • 0 argumente: `./ferma` → folosește `ferma.txt` ca intrare și `ferma.out` ca ieșire (valori default)
    • 2 argumente: `./ferma input.txt output.out` → folosește `input.txt` ca intrare și `output.out` ca ieșire
  • Exemplu: `int main(int argc, char* argv[])` unde `argc` = numărul de argumente, `argv` = vectorul de argumente

5. Punctaj (10p + până la 5p bonus)

5.1 Punctaj Teste (9p)

  • 18 teste automate × 0.5p = 9 puncte
  • Fiecare test verifică o configurație diferită de fermă
  • Pentru a trece un test, trebuie să atingi suma minimă specificată în fișierul:
    • teste/limite_minime.txt - conține minimul de bani necesar pentru fiecare test

5.2 Fișier README.md (1p)

  • Nume și grupă
  • OS și IDE folosit
  • Explicația organizării funcției int main
  • Strategia de maximizare a sumei finale (2-3 propoziții)

5.3 Punctaj Bonus - Clasament (până la 5p)

Clasament Live: rezultate.eu Actualizare automată la fiecare push în GitHub!

Puncte bonus pentru top 20 în clasament (bazat pe scorul total de bani):

Poziție Puncte Bonus
🥇 Locul 1 +5p
🥈 Locurile 2-3 +4p
🥉 Locurile 4-5 +3p
Locurile 6-10 +2p
Locurile 11-20 +1p

Cum funcționează:

  • Clasamentul se calculează după suma totală de bani obținută pe toate cele 18 teste
  • Doar studenții apar în clasamentul principal
  • Nickname-ul tău e generat automat (ex: “BraveDragon”, “MightyFalcon”)
  • Poți edita nickname-ul cu o cheie unică (vezi secțiunea 6.3)

Notă: Dacă tema nu compilează sau nu trece niciun test, va fi notată cu 0 puncte.

6. Încărcare și Testare

6.1 Accept Assignment

După accept:

  1. Se creează repository-ul tău: Laborator-POO-2025-2026/tema2-USERNAME
  2. Intră în folder: cd tema2-USERNAME

6.2 Compilare și Rulare

Comenzi disponibile:

make              # Compilează și rulează toate cele 18 teste
make build        # Doar compilează (creează executabilul)
make run          # Compilează și rulează ferma.txt (trebuie să existe în folder!)
make clean        # Curăță fișierele generate

Testare individuală:

make test1        # Rulează doar testul 1
make test5        # Rulează doar testul 5
make test-all     # Rulează toate testele (același cu make)

Când rulezi un test individual (ex: make test1), vei primi:

  • Mesaj detaliat cu eroarea dacă testul a picat (linia exactă și motivul)
  • Suma finală de bani obținută
  • Limita minimă necesară pentru a trece testul
  • Fișierul teste/limite_minime.txt conține minimul de bani pentru fiecare test

6.3 Clasament și Nickname

Clasament Live: Accesează rezultate.eu pentru a vedea clasamentul în timp real.

Nickname auto-generat:

  • La prima trimitere (git push), primești un nickname random (ex: “SwiftFalcon”, “BraveDragon”)
  • Mesajul de trimitere îți arată nickname-ul: 🎯 Nickname-ul tău: BraveDragon

Editare nickname (opțional):

make key          # Generează o cheie unică în teste/scripturi/key.txt
                  # Dacă cheia există deja, o afișează (nu generează alta)
 
# Apoi:
git add teste/scripturi/key.txt
git commit -m "Add personal key"
git push
 
# Pe rezultate.eu:
# 1. Găsește-te în clasament
# 2. Click pe ✏️ lângă numele tău
# 3. Introdu cheia din teste/scripturi/key.txt
# 4. Alege un nickname nou (3-30 caractere, alfanumeric + . _)

Dacă rulezi make key oricând ulterior, îți va afișa cheia generată anterior (nu creează una nouă).

6.4 GitHub Actions - Testare Automată

Testare și trimitere automată la fiecare git push!

Ce se întâmplă când faci push:

  1. 1️⃣ GitHub Actions pornește automat
  2. 2️⃣ Compilează programul (make build)
  3. 3️⃣ Rulează toate cele 18 teste
  4. 4️⃣ Trimite rezultatele la rezultate.eu
  5. 5️⃣ Actualizează clasamentul live

Vezi rezultatele:

  • GitHub: Tab “Actions” în repository

Output GitHub Actions:

✓ VERIFICARE REUSITA 🎉
Fisierul este valid!
Suma finala: 10 702 303 RON

✓ Rezultate trimise cu succes la server!
🎯 Nickname-ul tău: BraveDragon
   Vezi clasamentul pe: https://rezultate.eu

7. Exemplu Complet

ferma.txt
2 2 10 300 2
morcov 3 50 200
ceapa 2 40 160
ROTATIE 2
morcov ceapa
ceapa N/A

Strategie optimă:

ferma.out
1 planteaza 00x00 ceapa
1 planteaza 00x01 ceapa
3 culege 00x00
3 culege 00x01
4 planteaza 00x00 morcov
4 planteaza 00x01 morcov
7 culege 00x00
7 culege 00x01
8 planteaza 00x00 ceapa
8 planteaza 00x01 ceapa
10 culege 00x00
10 culege 00x01
SUMA_FINALA: 1040

Calcul sumă finală:

  • Cheltuieli: 2×40 (cepe zi 1) + 2×50 (morcovi zi 4) + 2×40 (cepe zi 8) = 80 + 100 + 80 = 260 RON
  • Venituri: 2×160 (cepe zi 3) + 2×200 (morcovi zi 7) + 2×160 (cepe zi 10) = 320 + 400 + 320 = 1040 RON
  • Suma finală: 300 (inițial) + 1040 - 260 = 1080 RON

8. Tips & Tricks

⚡ Strategii de Maximizare:

  • ✅ Calculează profit/zi pentru fiecare legumă: (preț_vânzare - cost) / timp_cultivare
  • ✅ Prioritizează legumele cu profit/zi ridicat
  • ✅ Folosește toate pătratele disponibile
  • NU planta legume care nu ajung la maturitate înainte de finalul simulării
  • ✅ Respectă rotațiile pentru a maximiza utilizarea pătratelor
  • ✅ Gestionează bugetul prudent - nu rămâne fără bani!

✅ Checklist Înainte de Submit:

  1. [ ] Compilează fără erori (make build)
  2. [ ] Trece toate testele local (make)
  3. [ ] README.md completat
  4. [ ] Commit + push pe GitHub
  5. [ ] Verificat Actions (tab “Actions”)
  6. [ ] Verificat clasament pe rezultate.eu

📁 Fișiere Importante:

  • teste/limite_minime.txt - limite minime pentru fiecare test
  • teste/scripturi/key.txt - cheia ta unică (opțional, pentru editare nickname)
  • Makefile - comenzi de compilare și testare

🔗 Link-uri Utile:

poo-is-ab/tema/2025/02.1762106356.txt.gz · Last modified: 2025/11/02 19:59 by marius.trifu
CC Attribution-Share Alike 3.0 Unported
www.chimeric.de Valid CSS Driven by DokuWiki do yourself a favour and use a real browser - get firefox!! Recent changes RSS feed Valid XHTML 1.0