gitweb on Svarog
projekti pod git sistemom za održavanje verzija -- projects under the git version control system--- a/skripta-spa1-sadrzaj.tex
+++ b/skripta-spa1-sadrzaj.tex
String = ARRAY [1..30] OF CHAR;
\end{codeblock}
-Operacije nad stringovima se najčešće uvoze iz modula \kod{Str}. One
-sve prihvataju \emph{otvorene nizove znakova} (strukture definisane sa
-\kod{ARRAY OF CHAR}), tako da im se može proslediti niz proizvoljne
-dužine.
+Budući da Modula 2 definiše mogućnost korišćenja \emph{otvorenih
+ nizova}, lako je moguće definisati procedure koje kao parametre
+primaju bilo koji tip koji je definisan kao niz znakova.
+
+\begin{codeblock}
+ PROCEDURE ObradaStringa(str: ARRAY OF CHAR);
+\end{codeblock}
+
+Konkretne promenljive u programu moraju biti definisane dužine.
+
+Operacije nad stringovima se najčešće uvoze iz modula \kod{Str} i one
+su sve definisane da prihvataju \emph{otvorene nizove znakova} kao što
+je malopre objašnjeno.
Određivanje stvarne dužine stringa (tj koliko od maksimalnog
kapaciteta niza je zapravo zauzeto sadržajem) se može izvesti na
Leksikografsko poređenje dva stringa se ne može vršiti standardnim
operatorima kao što su \kod{< > =}. Ovo je delom zato što se radi o
-nizovima, a delom i zato što se ne vidi direktno koji deo niza je
-popunjen stvarnim sadržajem. Za ovo se koristi komanda \kod{Compare},
-koja prihvata dva stringa kao parametre, a vraća broj koji predstavlja
-njihov odnos. Taj broj će biti 0 ako su stringovi jednaki, veći
-od nule ako je prvi string ``veći'', i manji od nule ako je prvi
-string ``manji''. Ovo se lako pamti kad primetimo da je odnos
-između \kod{Compare} i 0 isti kao i između prvog i drugog stringa.
+nizovima, ali značajnije i zato što se ne vidi direktno koji deo niza
+je popunjen ``stvarnim'' sadržajem. Za ovo se koristi komanda
+\kod{Compare}, koja prihvata dva stringa kao parametre, a vraća broj
+koji predstavlja njihov odnos. Taj broj će biti 0 ako su stringovi
+jednaki, veći od nule ako je prvi string ``veći'', i manji od nule ako
+je prvi string ``manji''.
\begin{codeblock}
IF Compare(str1, str2) > 0 THEN
END;
\end{codeblock}
+Ovo se lako pamti kad primetimo da je odnos između \kod{Compare} i 0
+isti kao i između prvog i drugog stringa.
+
Postoji i modul \kod{Strings} koji ima nešto drugačije definisane
procedure, no na njih se sada nećemo fokusirati.
tome resetovati na \kod{FALSE}, pa na ovo treba obratiti pažnju pri
radu.
+\subsubsection*{Mogući problemi}
+
+U ovoj glavi će biti navedeni neki česti problemi koji se mogu desiti
+pri korišćenju FIO modula, a koji su vezani za konkretnu
+implementaciju u XDS distribuciji kompajlera.
+
+\paragraph{\kod{RdStr} i drugi pozivi} Prilikom čitanja iz fajlova
+može doći do neobičnih rezultata ako se kombinuju pozivi \kod{RdStr}
+sa drugima. Problem je u različitom tretiranju separatora. Komanda
+\kod{RdStr} uvek čita do kraja reda i pri tome premesti poziciju za
+čitanje odmah iza znaka za razdvajanje redova. Ostale komande prvo
+preskaču separatore i čitaju sadržaj dok ne naiđu na novi separator
+(što može biti novi red, a može biti i razmak, tabulator i neki drugi
+znaci) i staju sa čitanjem \emph{pre} tog separatora. Kombinaovanje
+ova dva pristupa može dovesti do toga da \kod{RdStr} nakon neke druge
+komande učita samo kraj trenutnog reda, a ne sledeći red kao što bi
+bilo očekivano.
+
+\paragraph{EOF i prazan red na kraju fajla} Svako čitanje iz fajla
+postavlja \kod{EOF} u skladu sa tim da li je komanda stigla do kraja
+fajla ili ne. Nažalost kod svih komandi za čitanje (osim \kod{RdStr})
+postoji problem ukoliko je na kraju prazan red ili neki dodatni
+separator. Tada učitavanje poslednjeg elementa nije zapravo došlo do
+kraja fajla. Ako se nakon toga proba još jedno učitavanje sa takvom
+komandom ona će probati da preskoči separator i da učita neki sadržaj,
+ali će se zaglaviti jer ne može da ga nađe. Ovo ponašanje je greška u
+implementaciji FIO modula u okviru XDS distribucije.
+
\subsection{Zadatak: ispis sadržaja fajla na ekran}
Potrebno je sve redove iz fajla učitati i ispisati ih na ekran.
-\begin{lstlisting}[style=codeblock]
-MODULE ispis;
-FROM FIO IMPORT File, Open, Close, EOF, RdStr;
-FROM InOut IMPORT WriteString, WriteLn, ReadString;
-
-PROCEDURE ispisF(ime: ARRAY OF CHAR);
-VAR
- f:File;
- s : ARRAY[1..100] OF CHAR;
-BEGIN
- f:=Open(ime);
- EOF := FALSE;
- WHILE NOT EOF DO
- RdStr(f,s);
- WriteString(s);
- WriteLn;
- END;
- Close(f);
-END ispisF;
-
-VAR
- ime: ARRAY[1..100] OF CHAR;
-BEGIN
- WriteString("unesite ime fajla:");
- ReadString(ime);
- ispisF(ime);
-END ispis.
-\end{lstlisting}
+\lstinputlisting[style=codeblock]{kodovi/fajlovi/ispis.mod}
\subsection{Zadatak: spisak studenata}
podatak o jednom studentu, redom prezime, ime i godina rođenja,
razdvojeni razmacima.
-\begin{lstlisting}[style=codeblock]
-MODULE nizslog;
-FROM InOut IMPORT WriteString, WriteLn,
- WriteCard, ReadCard, ReadString;
-FROM FIO IMPORT File, Open, Create, Close, EOF,
- RdItem, RdCard, WrStr, WrCard, WrLn;
-FROM Str IMPORT Compare;
-
-CONST
- MaxStud = 100;
-TYPE
- String = ARRAY[1..30] OF CHAR;
- Student = RECORD
- ime, prez: String;
- god: CARDINAL;
- END;
- Studenti = ARRAY[1..MaxStud] OF Student;
-
-PROCEDURE UcitajF(fajl:String;
- VAR spisak: Studenti; VAR n:CARDINAL);
-VAR
- f:File;
-BEGIN
- n:=0;
- f:= Open(fajl);
- EOF := FALSE;
- WHILE NOT EOF DO
- INC(n);
- RdItem(f, spisak[n].prez);
- RdItem(f, spisak[n].ime);
- spisak[n].god := RdCard(f);
- END;
- Close(f);
-END UcitajF;
-
-PROCEDURE Ispisi(spisak:Studenti; n:CARDINAL);
-VAR
- i: CARDINAL;
-BEGIN
- FOR i:=1 TO n DO
- WriteString(spisak[i].prez);
- WriteString(" ");
- WriteString(spisak[i].ime);
- WriteString(" ");
- WriteCard(spisak[i].god,1);
- WriteLn;
- END;
-END Ispisi;
-
-PROCEDURE IspisiF(fajl:String;
- spisak:Studenti; n:CARDINAL);
-VAR
- f:File;
- i: CARDINAL;
-BEGIN
- IF (n>0) AND (n<=MaxStud) THEN
- f:=Create(fajl);
- (* pravimo takav fajl da ne
- postoji zadnji prazan red *)
- FOR i:=1 TO n-1 DO
- WrStr(f,spisak[i].prez);
- WrStr(f," ");
- WrStr(f,spisak[i].ime);
- WrStr(f," ");
- WrCard(f,spisak[i].god,1);
- WrLn(f);
- END;
- WrStr(f,spisak[n].prez);
- WrStr(f," ");
- WrStr(f,spisak[n].ime);
- WrStr(f," ");
- WrCard(f,spisak[n].god,1);
- Close(f);
- END;
-END IspisiF;
-
-PROCEDURE NoviStudent(VAR spisak:Studenti;
- VAR n:CARDINAL);
-VAR
- stud,temp:Student;
- i:CARDINAL;
- dodaj:BOOLEAN;
-BEGIN
- IF n<MaxStud THEN
- WriteString("Prezime novog studenta?");
- ReadString(stud.prez);
- WriteString("Ime novog studenta?");
- ReadString(stud.ime);
- WriteString("Godina rodjenja");
- WriteString("novog studenta?");
- ReadCard(stud.god);
- (* proverimo da li vec postoji *)
- i:=1;
- dodaj := TRUE;
- WHILE (i<=n) AND dodaj DO
- temp := spisak[i];
- IF (temp.god = stud.god) &
- (Compare(temp.prez,stud.prez)=0) &
- (Compare(temp.ime,stud.ime)=0) THEN
- dodaj:=FALSE;
- END;
- INC(i);
- END;
- IF dodaj THEN
- INC(n);
- spisak[n]:=stud;
- ELSE
- WriteString("podaci vec postoje!");
- END;
- ELSE
- WriteString("popunjen kapacitet!");
- END;
-END NoviStudent;
-
-VAR
- spisak : Studenti;
- fajl:String;
- n:CARDINAL;
-BEGIN
- fajl:="studenti.txt";
- UcitajF(fajl, spisak, n);
- Ispisi(spisak, n);
- NoviStudent(spisak,n);
- IspisiF(fajl, spisak, n);
-END nizslog.
-\end{lstlisting}
+\lstinputlisting[style=codeblock]{kodovi/fajlovi/nizslog.MOD}
\sectionbreak
\section{Liste i pokazivači}