This is an old revision of the document!


Tema 2. A Game of Scrabble

  • Data publicării: 22.11.2020
  • Deadline soft: TODO
  • Deadline soft: TODO

Actualizări: TODO

Scopul temei:

  • utilizarea și lucrul cu șiruri de caractere;
  • înțelegerea unui joc și implementarea acestuia în limbajul de programare C

Introducere

Tema se bazeaza pe o forma a jocului de Scrabble in care va trebui sa folositi in mod special matrici si functii pentru prelucrarea sirurilor de caractere. Scopul final este implementarea completa a jocului astfel incat doi participanti (programul vostru impotriva checker-ului) sa poata sa joace alternativ si sa se determine un castigator.

Descriere

Jocul are la baza doua table de joc pastrate sub forma unor matrici patratice de dimensiune 15 x 15. O tabla (matrice) va pastra cuvintele “jucate” de cei doi jucatori pe parcursul jocului, in timp ce cealalta tabla va fi folosita pentru a marca casute ce ofera punctaj bonus.

Pentru claritate, vom folosi termenul de tabla de joc pentru a ne referi la matricea care stocheaza cuvinte si tabla de bonusuri pentru matricea care va stoca pozitiile ce ofera puncte bonus in joc.

Tabla de joc

Tabla de joc va contine cuvinte atat pe lungime, cat si pe latime. Fiecare casuta din matrice va stoca un singur caracter dintr-un cuvant sau caracterul ‘.’ daca este goala.

Initial veti avea o matrice de caractere cu dimensiunea 15 x 15 in care fiecare element din matrice va contine caracterul ‘.’ (deoarece nu avem niciun cuvant salvat la inceput). In exemplul de mai jos este o matrice in care au fost inserate mai multe cuvinte: “CAT”, “AIRPLANE”, “TRAIN”, “PROGRAM”, “LECTURE”.

Tabla de punctaj bonusuri

Aceasta tabla (bonus_board) este deja data in fisierul header (scrabble.h) ce se afla in arhiva cu checker-ul si va ramane neschimbata pe parcursul intregii teme.

Aceasta tabla va avea aceeasi dimensiune ca si tabla de joc, de 15 X 15. Tabla este populata cu valori de 0, 1 si 2 cu urmatoarea semnificatie: 0 - niciun bonus 1 - punctajul se dubleaza daca pe patratica respectiva se afla o litera apartinand unui cuvant care are substringul “XX” in compozitie, se da substringul la fiecare joc 2 - punctajul se tripleaza daca pe patratica respectiva se afla o litera apartinand unui cuvant care se termina cu substringul “XX”, se da substringul la fiecare joc

Modul in care se calculeaza punctajul va fi detaliat ulterior in cerintele temei. Matricea arata in felul urmator:

Lista de cuvinte

Pe langa table de bonusuri, in fisierul header scrabble.h din arhiva veti mai primi un vector de cuvinte pe care il veti folosi la anumite task-uri din tema. Vectorul se cheama words si contine 100 de string-uri.

Atentie! Pentru fiecare cerinta veti primi datele de intrare la standard input. De fiecare data primul input pe care il va primi programul vostru este numarul taskului (0-5 pentru tema, 6 pentru bonus) urmand ca mai apoi sa cititi restul de date asa cum este descris pentru fiecare cerinta in parte.

Cerinte

Veți avea de rezolvat 6 cerințe obligatorii și o cerință bonus.

Cerinta 1: (18 Puncte) - 9 teste

Pentru aceasta cerinta va trebui sa cititi numarul intreg N urmat de N linii continand coordonatele unui cuvant si cuvantul respectiv. Dupa ce faceti citirea unei linii, adaugati-o la coordonatele corespunzatoare in matricea de joc (cea pe care ati declarat-o la cerinta 0). Cuvantul va fi pastrat caracter cu caracter in matrice incepand cu coordonatele date.

Dupa ce ati salvat toate cele N cuvinte puteti sa afisati matricea apeland functia de afisare in felul urmator print_board(game_board).

Atentie! Matricea in care pastrati cuvintele va trebui sa aiba caracterul ‘.’ pe pozitiile neocupate pentru ca functia de afisare sa functioneze.

Se da un input de forma:

1
N
Y1 X1 D1 WORD1
Y2 X2 D2 WORD2
…
N -> numar de cuvinte primite
Yi -> indicele pe verticala unde va fi plasat cuvantul (linia in matrice)
Xi -> indicele pe orizontala unde va fi plasat cuvantul (coloana in matrice)
Di -> directia in care este scris cuvantul: 
* Daca D == 0: cuvantul e scris pe orizontala, de la (Yi, Xi) spre dreapta
* Daca D == 1: cuvantul e scris pe verticala, de la (Yi, Xi) in jos
Yi - indicele liniei unde este plasata prima litera din cuvant 
Xi - indicele coloanei unde este plasata prima litera din cuvant
(Yi, Xi) - pozitia de unde incepe cuvantul, de la

Atentie! Numerotarea liniilor se face din coltul stanga sus si incepand cu indicele 0!

Atentie! Pentru acest task se garanteaza ca nu vor fi date cuvinte care sa iasa din dimensiunile tablei.

Un exemplu de input este urmatorul:

1
5
4 4 0 CAT
4 6 1 TRAIN
6 6 0 AIRPLANE
6 9 1 PROGRAM
6 10 1 LECTURE

Acest input va produce urmatorul output:

Cerinta 2: (20 Puncte) - 10 teste

Pentru aceasta cerinta va trebui sa calculati punctajul obtinut de doi jucatori fara a tine cont de punctele bonus. Veti primi un input exact ca la task-ul precedent, dar de aceasta data veti afisa punctajul total al celor doi jucatori.

Calcularea scorului unui cuvant se face prin insumarea scorului fiecarei litere din cuvant. Scorurile literelor sunt urmatoarele:

A, E, I, L, N, O, R, S, T, U - 1 Punct
D, G - 2 Puncte
B, C, M, P - 3 Puncte
F, H, V, W, Y - 4 Puncte
K - 5 Puncte
J, X - 8 Puncte
Q, Z - 10 Puncte

Tip! Pentru a tine informatiile pentru scorurile fiecarei litere puteti tine un vector de dimensiune 26 cu toate valorile puse in ordine alfabetica. Pentru a afla la ce index in vector se afla scorul unei litere, substrageti valoarea ‘A’ din litera cautata.

Atentie! Doar pentru acest task nu se va tine cont de tabla de bonusuri!

Se da un input de forma:

2
N
Y1 X1 D1 WORD1
Y2 X2 D2 WORD2
…
Unde:
XX este substringul pentru bonusul primit pentru casutele marcate cu 1. 
YY este substringul pentru bonusurile primite pentru casutele marcate cu 2.
N este numarul de cunvinte
Xi, Yi, WORDi sunt coordonatele pentru cuvantul WORDi
Di este directia in care este scris cuvantul

Output-ul va fi sub forma urmatoare:

Player 1: W Points
Player 2: T Points

W este scorul obtinut de primul jucator.
T este scorul obtinut de al doilea jucator.
Textul pentru fiecare jucator va fi afisat pe o linie separata.

Un exemplu de input este urmatorul:

2
5
4 4 0 CAT
4 6 1 TRAIN
6 6 0 AIRPLANE
6 9 1 PROGRAM
6 10 1 LECTURE 

Pentru acest input se obtine outputul urmator:

Player 1: 24 Points
Player 2: 17 Points

Explicatie:

Jucatorului 1 ii revin urmatoarele cuvinte din input: “CAT”, “AIRPLANE”, “LECTURE”
Scor(Jucator 1) = Scor(“CAT”) + Scor(“AIRPLANE”) + Scor(“LECTURE”)
Scor(Jucator 1) = (3 + 1 + 1) + (1 + 1 + 1 + 3 + 1 + 1 + 1 + 1) + (1 + 1 + 3 + 1 + 1 + 1 + 1) 
Scor(Jucator 1) = 5 + 10 + 9 = 24
Scor(Jucator 2) = Scor(“TRAIN”) + Scor(“PROGRAM”) = 5 + 12 = 17

Format input

Fisierul de intrare, in care se afla informatiile despre fiecare task, se numeste input.txt. Acesta are urmatoarea structura:

  • Pe prima linie se va gasi numele fisierului binar ce reprezinta imaginea in format bmp care va fi prelucrata ulterior si are formatul descris la inceput (aceasta are cu siguranta extensia .bmp, pentru a va putea fi mai usoara creearea numelor imaginilor de output)
  • Pe a doua linie se va gasi numele fisierului text ce reprezinta filtrul ce trebuie aplicat la task-ul 3 (semnificatia acestuia este gasita la descrierea task-ului aferent)
  • Pe a treia linie se va gasi numele fisierului text ce reprezinta filtrul de pooling ce trebuie aplicat la task-ul 4 (semnificatia acestuia este gasita la descrierea task-ului aferent)
  • Pe a patra linie se va gasi numele fisierului text ce contine valoarea de threshold necesara aplicarii algoritmului de clustering de la task-ul 5

Format filtru:

N
VAL_11 VAL_12 ... VAL_1N
VAL_21 VAL_22 ... VAL_2N
........................
VAL_N1 VAL_N2 ... VAL_NN
  • N: dimensiunea filtrului
  • VAL_IJ: valoarea filtrului de tip double de pe linia i si coloana j

Format filtru pooling:

m/M N
  • primul caracter area valoarea m daca filtrul este de minim, iar M daca este de maxim
  • N: dimensiunea filtrului

Exemplu

input.txt
test1.bmp
./input/filters/filter1.txt
./input/pooling/pooling1.txt
./input/clustering/cluster1.txt

Exemple de imagini in format bmp si de input-uri pentru task-uri gasiti in directorul input din checker.

Cand scrieti imagini in format BMP, intre ultimul byte din header si byte-ul la care incepe matricea de pixeli (adica pana la byte-ul de offset) trebuie sa scrieti peste tot byte-ul 0.

Format output

Dupa cum a fost descris deja, fiecare task are ca scop producerea unei noi imagini, dupa aplicarea unei operatii de procesare pe imaginea initiala. Prin urmare, programul vostru va trebui sa citeasca imaginea de input si sa produca 5 imagini noi, fiecare avand numele specificat in cadrul task-ului corespunzator.

Bineinteles, puteti sa sariti peste implementarea unui task sau sa implementati selectiv un anumit numar de taskuri, singura restrictie pe care o aveti este sa nu primiti erori de tipul Segmentation fault, deoarece acestea vor invalida testarea temei.

Resurse si checker-ul local

Resursele pentru tema se pot descarca de aici. Sunt prezente:

  • bmp_header.h: headerul care contine declaratiile struct-urilor pe care le veti folosi in citirea unui fisier BMP;
  • checker.zip: arhiva zip ce contine checker-ul cu care puteti sa va testati implementarea local.

Trimitere tema

Tema va fi trimisa folosind v2.vmchecker, cursul Programarea Calculatoarelor, tema Image Processing.

Punctajul:

  • 110p - teste (20p sunt bonus)
    • 10 teste
    • 9p pe test
    • 20p pentru rularea fara erori a utilitarului valgrind pe imaginea cea mai mare (doar daca aveti deja 90p)
  • 10p - coding style & README (checker-ul o sa va acorde aceste puncte doar pentru prezenta fisierului README, la corectare acestea vor fi validate)

Restrictii si precizari

  • Nu folositi variabile globale.
  • Fiti consistenti in ceea ce priveste Coding Style-ul.
  • Toate matricile si vectorii folositi se vor aloca dinamic, pe heap;
  • Task-ul 2 este singurul in care aveti de modificat si headerele imaginii bmp, in rest nu veti avea de modificat nimic in headerele imaginii;
  • Tema se va trimite pe vmchecker si se va testa local cu ajutorul checker-ului care va fi disponibil in curand;
  • Pe vmchecker veti uploada o arhiva in format .zip care sa contina:
    1. Makefile, cu cel puțin 3 targeturi, build, run și clean; Regula run trebuie sa ruleze executabilul care a fost obtinut la regula build si care are numele bmp (vezi si task-ul bonus);
    2. sursele voastre, adică fișierele .c și .h. Inclusiv headerul bmp_header.h sau sub orice altă denumire îl folosiți;
    3. README, în care trebuie să dați detalii despre implementare, de ce ați ales să rezolvați într-un anumit fel, etc.
  • Daca rezolvati doar o parte din task-uri asigurati-va ca pe celelalte nu primiti erori la rulare (precum SEGFAULT) sau time limit exceeded, altfel tot testul va fi punctat cu 0. De exemplu, daca task-urile 1 si 2 sunt OK dar task-ul 3 primeste SEGFAULT sau dureaza prea mult atunci tot testul se va nota cu 0.

Temele care nu folosesc alocare dinamica vor avea o depunctare de pana la 50 de puncte din punctajul temei, in functie de gravitate! De asemenea, nu va fi acordat punctajul pe bonus in acest caz!

Nu descarcati imaginile atasate in enunt pentru testare! Acestea nu respecta formatul BMP! Pentru testare folositi numai imaginile puse la dispozitie in arhiva de testare. Imaginile de mai sus au doar caracter informativ.

Listă depunctări

Lista nu este exhaustivă. Se pot aplica chiar depunctări mai mari în cazuri excepționale.

  • o temă care nu compilează și nu a rulat pe vmchecker nu va fi luată în considerare
  • o temă care nu rezolvă cerința și trece testele prin alte mijloace nu va fi luată în considerare
  • [-50.0]: o tema care nu folosește deloc alocarea dinamică (-70.0 dacă aceasta ia și punctajul bonus)
  • [-1.0]: warning-uri la compilare (este obligatorie folosirea în fișierul Makefile a flag-ului de compilare -Wall pentru regula build)
  • [-1.0]: numele variabilelor nu sunt sugestive
  • [-1.0]: linii mai lungi de 80 de caractere in cod / in fișierul README
  • [-1.0]: cod nemodular, funcții prea lungi (inclusiv main)
  • [-2.5]: variabile globale
  • [-5.0]: abordare ineficientă
    • în cadrul cursului de programare nu avem ca obiectiv rezolvarea în cel mai eficient mod posibil a programelor; totuși, ne dorim ca abordarea să nu fie una ineficientă, de genul să nu folosiți instrucțiuni repetitive acolo unde clar nu era cazul, etc.
programare/test2_scrabble.1605999801.txt.gz · Last modified: 2020/11/22 01:03 by laurentiu.stefan97
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