2024(e)ko otsailaren 24(a), larunbata

6. astea | zenbaki konbinatorioa (funtzioa)








zenbaki konbinatorioa, kopuru osoa da eta hura lortzeko m eta n zenbaki osoak eta positiboak ezagutu behar dira. Jakinik ere, zenbaki negatiboen faktoriala definiturik ez dagoelako datuek baldintza hau betetzen dutela:   m >= n.

Ondoko programa honek ZenbakiKonbinatorioaMonolitikoa.pas zenbaki konbinatorioa kalkulatzen du, baina aintzat hartu beharra dago programak inolako barne antolaketarik ez duelako faktorialaren kalkulua hiru aldiz egiten duela:

Aurreko programaren beste bertsio bat ondoko irudian erakusten da, ZenbakiKonbinatorioaFuntzioz.pas izeneko bertsio berri horrek programa nagusian datuak irakurri ondoren fnliFaktoriala() izeneko funtzioa hiru aldiz deia egiten dio. Funtzio horrek programa nagusiko datu bat jasotzen du eta dagokion faktoriala kalkulatu eta programa nagusiari itzultzen dio:
program ZenbakiKonbinatorioa_Funtzioz ;

function fnliFaktoriala(iZbk : integer) : longint ;
var
    iKontagailua : integer ;
    liMetagailua : longint ;
begin
    liMetagailua := 1 ;
    for iKontagailua:=1 to iZbk do
       liMetagailua := liMetagailua * iKontagailua ;

    fnliFaktoriala := liMetagailua ;
end ;

{ ----------PROGRAMA NAGUSIA---------- }
var
    iZbkM, iZbkN, iZbkM_N, iEmaitza : integer ;
    liFaktM, liFaktN, liFaktM_N : longint ;

begin
    repeat
        write('m zenbaki osoa eta positiboa eman: ') ;
        readln(iZbkM) ;
        write('n zenbaki osoa (non n <= m ): ') ;
        readln(iZbkN) ;
    until (iZbkN >= 0) AND (iZbkM >= iZbkN) ;

    liFaktM := fnliFaktoriala(iZbkM) ;

    liFaktN := fnliFaktoriala(iZbkN) ;

    iZbkM_N := iZbkM - iZbkN ;
    liFaktM_N := fnliFaktoriala(iZbkM_N) ;

    iEmaitza := liFaktM div (liFaktN * liFaktM_N) ;

    write('Zenbaki konbinatorioa ---> ', iZbkM, '! div (', iZbkN,'! * ', iZbkM-iZbkN,'!)') ;
    write(' = ', iEmaitza) ;

    readln ;
end.

Hona hemen ZenbakiKonbinatorioaFuntzioz.pas programaren azalpenak:
  • fnliFaktoriala() izeneko funtzioaren sarrera bakarra integer bat izanik, bere irteera longint bat da
  • fnliFaktoriala() funtzioak parametro formal bakarra du eta bere izena iZbk da
  • fnliFaktoriala() funtzioak bi aldagai laguntzaile behar ditu iKontagailua eta liMetagailua (bertako aldagaiak deitzen dira)
  • fnliFaktoriala() funtzioari hiru aldiz deia egiten zaio programa nagusian, uneko parametroak iZbkM, iZbkN eta iZbkM_N direlarik
  • fnliFaktoriala() funtzioak, funtzio guztiek bezala, dei bakoitzean emaitza bakarra itzuliko dio programa nagusiari
  • fnliFaktoriala() funtzioak, funtzio guztiek bezala, emaitza kanporatzeko berari dagokion fnliFaktoriala etiketaren bitartez egiten du
 

2024(e)ko otsailaren 22(a), osteguna

6. ASTEA | ikasgelan egindakoa

 6. astea (2024/02/26 eta 2024/03/01) ikasgelan egin dena

  • Blogeko Algoritmoak artikulua azaldu dugu bide hau jarraituz:
    • Algoritmoaren kontzeptua
    • Ezagutzen ditugun algoritmo batzuk
    • Algoritmoen adierazpideak
    • Algoritmo baten adibidea
  • Blogeko 5. astea | Menu bat ariketa ezaguna zaigu eta duen berezitasuna: aldagai aukeratzailea karaktere bat da. Menuak egiten ikasi dugu eta ikusi adibide honetan aukerak hautatzeko CHAR motako datua erabiltzen dela.
  • Azken ostiralekoa errepikatuz, AlfabetoLarriarenZatia.pas programaren bitartez, ondoko hauek erabiltzeko crt unitatearen beharraz hitz egin dugu:
    • readkey funtzioa
    • keypressed funtzioa
    • clrscr prozedura
    Hauxe da AlfabetoLarriarenZatia.pas programa:
program AlfabetoLarriarenZatia ;
uses
   crt ;
var
   cLetra: char ;
   cLehenLetra: char ;
   cAzkenLetra: char ;
begin
   clrscr ;
   writeln ;
   writeln ;
   repeat
      write('''A'' eta ''Z'' arteko lehen letra bat eman: ') ;
      cLehenLetra := readkey ;
      writeln(cLehenLetra) ;
   until (cLehenLetra >= 'A') and (cLehenLetra <= 'Z') ;
   
   writeln ;
   repeat
      write('''', cLehenLetra, ''' eta ''Z'' arteko azken letra bat eman: ') ;
      cAzkenLetra := readkey ;
      writeln(cAzkenLetra) ;
   until (cAzkenLetra >= cLehenLetra) and (cAzkenLetra <= 'Z') ;
   
   writeln ;
   writeln('     Karakterea        Kodea') ;
   writeln('     ----------        -----') ;

   for cLetra:=cLehenLetra to cAzkenLetra do
   begin
      writeln(cLetra:15, ' -----> ', ord(cLetra)) ;
   end ;
   
   writeln('     ----------        -----') ;
   writeln('     Karakterea        Kodea') ;            
   
   writeln ;
   repeat until keypressed ;   
   {
   writeln ;
   write('RETURN sakatu aurrera egiteko ') ;
   readln ;
   }
   {
   writeln ;
   repeat 
      writeln('keypressed = ', keypressed) ;
   until keypressed ;
   }
end.
  • AzpiprogramenZergatia.pdf eskuliburuan 6-5 eta 6-8 bitarteko orrialdeak irakurtzea komeniko zaizue:
    • 6. ATALA: AZPIPROGRAMAK, FUNTZIOAK ETA PROZEDURAK
      • 6-5 orrialdeko 6.1 SARRERA
      • 6-5 orrialdeko 6.2 AZPIPROGRAMA BATEN HELBURUA
      • 6-5 orrialdeko 6.2.1 Kodearen errepikapena ekiditea
      • 6-7 orrialdeko 6.2.2 Programaren antolaketa lortzea
      • 6-8 orrialdeko 6.2.3 Kodearen independentzia
    • Azpiprogramen abantailak:
      • Kodearen errepikapena ekiditea
      • Programaren antolaketa lortzea
        • Programa monolitikotik programa modularrera
        • Programaren erroreak bilatzea errazagoa zer modulutan agertzen den identifika daitekeelako
        • Programadore taldea
        • Programaren mantenua errazten da, programa modularra izatean aldaketak eta hobekuntzak egitea errazagoa da
      • Kodearen independentzia:
        • Kodearen berrerabilpena, modulu baten kodea programa batetik bestera eraman daiteke
        • Azpiprograma batean behar diren aldagai eta gainerako elementuak defini daitezke eta denak pribatuak dira
  • Blogeko 6. astea | zenbaki konbinatorioa (funtzioa) izenburua duen artikulutik abiatuta, honakoak ikusi ditugu:
    • Funtzio baten deia
    • Funtzio baten uneko parametroak
    • Funtzioa baten parametro formalak (bereziki, irteeraren datu-mota)
    • Funtzioak emaitza itzultzeko duen mekanismoa
    • Funtzioaren bertako aldagaiak

  • 1. kontroleko emaitza orokorrak:
    Guztiak        Aurkeztuak   
   Suspendituak      Aprobatuak  
   < 3      >= 3  |  < 5        >= 5  |  < 7   
   >= 7   
74 68 16 13 16 23
%100 %91,9 %23,5 %19,1 %23,5 %33,8
%42,6 %57,4
1. kontroleko emaitza orokorrak

  • Aurreko egunekoa errepikatuz, blogeko 6. astea | zenbaki konbinatorioa (funtzioa) izenburua duen artikulutik abiatuta, honakoak berriro ikusi ditugu:
    • Funtzio baten deia
    • Funtzio baten uneko parametroak
    • Funtzioa baten parametro formalak (bereziki, irteeraren datu-mota)
    • Funtzioak emaitza itzultzeko duen mekanismoa
    • Funtzioaren bertako aldagaiak
  • Blogeko 6. astea | zenbaki konbinatorioa (prozedura) izenburua duen artikulutik abiatuta, honakoak ikusi ditugu:
    • Prozedura baten deia
    • Prozedura baten uneko parametroak (sarrerakoak edo irteerakoak izan daitezke)
    • Prozedura baten parametro formalak
    • Prozedurak emaitzak itzultzen baditu nola egiten duen
    • Prozeduraren bertako aldagaiak
  • 6. astea | zenbaki bat asmatzen izenburua duen artikuluan proposatzen den ariketa hasi dugu, baina enuntziatua ikustetik eta programa exekutatetik ez gara pasatu
 
 

Algoritmoak

Algoritmo hitza, berez, IX. mendeko matematikari persiar baten izenetik eratortzen da: Al-Khwarizmi. Greziar tradizio matematikoak, nagusiki, geometriari buruz hitz egiten zuen, triangeluak, zirkuluak eta poligonoak bezalako formei buruz, eta azalera eta bolumena kalkulatzeko moduari buruz. Bestalde, Indiako matematikak kalkulua askoz sinpleagoa egiten zuen hamar sinboloko sistema hamartarrari esker. Al-Khwarizmiren ekarpena: Al-Khwarizmik greziar irudiak eta indiar sinboloak konbinatu zituen, gaur egun aljebra deitzen dugun pentsamendu matematikoari hasiera emanez.

XIX. mendean Ada Lovelace-k makina analitikoaren bidez Bernouilliren zenbakiak kalkulatzeko algoritmo bat idatzi zuen: zer eragiketa egin behar ziren, zer ordenan, zer aldagairen gainean, begiztak, baldintzen menpeko jauziak... Hori guztia ordenagailu baterako programa gisa har daiteke. Horregatik, historiako lehen programatzailetzat hartu izan da Lovelace.


Abu Abdallah Muḥammad ibn Mūsā al-Jwārizmī (arabieraz: أبو عبد الله محمد بن موسى الخوارزمي ابو جعفر‎; c. 780 – c. 850), Al-Khwarizmi izenaz ezaguna. Al-Khwarizmi (Sobiet Batasuneko seilua, 1983)


Ada Lovelace, Augusta Ada Byron (Lovelaceko kondesa). Historiako lehen programatzailea izan zela esan ohi da, eta Charles Babbageren konputagailu mekanikoaren gaitasuna erakutsi zuen


Ada Lovelace eredutzat har daitekeen bezala, historian izan dira beste emakume zientzialari asko. Hona hemen, mosaiko txiki bat:

Guzti horien artetik pare bat aipatzearren, ondoko bi hauek nabarmenduko
genituzke: Hedy Lamarr ingeniaria eta Sofia Kovalevskaia matematikaria

Jarraian ondoko hauek ikusiko ditugu:

  • Algoritmoaren kontzeptua
  • Ezagutzen ditugun algoritmo batzuk
  • Algoritmoen adierazpenak
  • Algoritmo baten adibidea


Problema informatiko bati erantzuna emateko lau urrtas hauek bete behar dira:
  1. Arazoaren definizioa
  2. Algoritmoa asmatu
  3. Algoritmoa programa bezala idatzi
  4. Soluzioa ebaluatu
Beraz programa bat idatzi aurretik algoritmo bat asmatu beharra daukagu. Baina algoritmoa zer da? Intuitibori erraz definitzen da: lan bat exekutatzeko behar diren instrukzioen multzoa da algoritmoa.

Algoritmo kontzeptuaren definizioa: Problema baten ebazpena lortzen duen pauso-sekuentzia finitu, ordenatu eta anbiguotasun gabekoa [Knuth, 1968]. Edozein programak algoritmo bat dauka bere baitan, algoritmoak independenteak dira programa idaztean erabilitako programazio-lengoaiarekiko zein programa exekutatzen duen ordenagailuarekiko.

Algoritmoen ezaugarriak:
  • Zehatza da (zalantzagarritasunik gabea)
  • Pausoen kopurua finitua da
  • Pausoen arteko ordena adierazi behar du
  • Bukatu egin behar du
  • Bi aldiz exekutatzean emaitza bera bueltatu behar du
  • Programazio-lengoaiarekiko independentea da
  • Dagokion programa exekutatzen duen ordenagailuarekiko independentea da


Dagoeneko programatzen ari garelako, konturatu ez garen arren, algoritmoak erabiltzen ari gara. Ikusitako algoritmo batzuei begirada bat bota diezaiegun:

Laster ikusiko ditugu beste algoritmo bi hauek: 6. astea | zenbaki bat asmatzen eta 6. astea | letra bat asmatzen. 



Algoritmoak adierazteko funtsean bi modu daude:
  • Lengoaia-naturala: sasikodea
  • Modu grafikoa: fluxu-diagrama edo organigrama

Algoritmoen adibiderik klasikoenak errezetak dira, jarraian Pedro Subijana maisu famatuaren “Denok Sukaldari” liburutik hartutako algoritmoa ematen da:



Algoritmoak ideiak transmititzeko tresnak direnez grafikoak izan daitezke, jostailuak muntatzeko orrietan agertzen diren bezalakoak:



Algoritmoak adierazteko fluxu-diagramak erabiltzen dira, Esate baterako, Grezia zaharrean Euklides matematikariak gure egunetara iritsi den algoritmoa asmatu zuen bi zenbakien zatitzaile komunetako handiena z.k.h. lortzeko. Hauxe da Euklidesen algoritmoari dagokion fluxu-diagrama:







Adibide honetan zenbaki sorta baten maximoa zehaztuko dugu. Hemen algoritmoa:

  1. Zehaztu zenbat zenbakik osatuko duten zenbakien sorta
  2. Sortaren lehen zenbakia irakurri
  3. Lehen zenbaki hori maximoa da
  4. Errepikatu zenbakien sorta amaitu arte:
    • Zenbaki berria irakurri
    • Zenbaki berria maximoa baino handiagoa bada maximoaren balioa berritu
  5. Maximoa erakutsi

Eta hemen algoritmo hori Pascal programazio-lengoaian ezarrita:
program ZenbakiSortaBatenMaximoa ;

uses
   crt ;
var
   iZenbakiKopurua, iZbk, iMaximoa, iKont : integer ;

begin
   clrscr ;
   writeln('Zenbaki positibo osoen sorta batean sartutako maximoa zehaztu') ;
   writeln('=============================================================') ;
   writeln ;
   
   (* --------------------------ALGORITMOAREN 1. URRATSA------------------ *)
   repeat
      write('Zenbaki osoen kopuru eman: ') ;
      readln(iZenbakiKopurua) ;
   until iZenbakiKopurua > 0 ;  
   writeln ;
   
   (* --------------------------ALGORITMOAREN 2. URRATSA------------------ *)
   repeat
      write('Lehen zenbaki positiboa eman: ') ;
      readln(iZbk) ;
   until iZbk > 0 ;
   
   (* --------------------------ALGORITMOAREN 3. URRATSA------------------ *)
   { lehen zenbakia iMaximoa da }
   iMaximoa := iZbk ;
   
   (* --------------------------ALGORITMOAREN 4. URRATSA------------------ *)
   for iKont:=2 to iZenbakiKopurua do
   begin
      repeat
         write(iKont, '. zenbaki positiboa eman: ') ;
         readln(iZbk) ;
      until iZbk > 0 ;
      
      if iZbk > iMaximoa then     { oraintxe sartutakoa handiagoa denean }
      begin
         iMaximoa := iZbk ;
      end ;
   end ;
   
   (* --------------------------ALGORITMOAREN 5. URRATSA------------------ *)
   writeln ;
   writeln('Maximoa = ', iMaximoa) ;
   
   repeat until keypressed ;
end.

Hauxe da programa horren balizko irteera bat:


Ikusi algoritmo honen programazio desberdinak:

 

2024(e)ko otsailaren 19(a), astelehena

Hurrengo bost asteak (6., 7., 8., 9. eta 10.)


Egutegia gogoratuz, ikastaroak aurrera darrai eta laster azterketa helduko da. Hona hemen hurrengo bost asteetan egiteko daukagunaren laburpena:

Astea Gaia Data Non
6.
Errepikakorrak eta CHAR datu-mota
2024/02/26
(T)
6.
(Azp3) errepikakorrak
2024/02/26
(M)
6.
(Azp1) errepikakorrak
2024/02/27
(M)
6.
(Azp2) errepikakorrak
2024/02/28
(M)
6.
CHAR datu-mota eta azpiprogramak
2024/02/29
(T)
7.
Azpiprogramak: zergatik, zertarako
2024/03/04
(T)
7.
 (Azp3) azpiprogramak: divide et impera
2024/03/04
(M)
7.
 (Azp1) azpiprogramak: divide et impera
2024/03/05
(M)
7.
(Azp2) azpiprogramak: divide et impera
2024/03/06
(M)
7.
 Azpiprogramak: divide et impera
2024/03/08
(T)
8.
Azpiprogramak eta STRING datu-mota
2024/03/11
(T)
8.
(Azp3) errepikakorrak eta karaktereak
2024/03/11
(L)
8.
 (Azp1) errepikakorrak eta karaktereak
2024/03/12
(L)
8.
(Azp2) errepikakorrak eta karaktereak
2024/03/13
(L)
8.
STRING datu-mota
2024/03/15
(T)
9.
STRING datu-mota eta ARRAY datu-mota
2024/03/18
(T)
9.
(Azp3) Azpiprogramak eta kateak
2024/03/18
(M)
9.
(Azp1) Azpiprogramak eta kateak
2024/03/19
(M)
9.
(Azp2) Azpiprogramak eta kateak
2024/03/20
(M)
9.
ARRAY datu-mota
2024/03/22
(T)
10.
ARRAY datu-mota eta RECORD datu-mota
2024/03/25
(T)
10.
(Azp3) arrayak eta erregistroak
2024/03/25
(L)
10.
(Azp1) arrayak eta erregistroak
2024/03/26
(L)
10.
(Azp2) arrayak eta erregistroak
2024/03/27
(L)
                 (L) Laborategia                              (M) Mintegia                               (T) Teoria                     

Gogoratu 11. astean azterketa izango duzuela:
  • Azp1, 2024-04-08an
  • Azp2, 2024-04-09an
  • Azp3, 2024-04-10ean

 

ReadKey funtzioa eta KeyPressed funtzioa

readkey funtzioak ez du parametrorik jasotzen, parametrorik ez duelako behar. Bere emaitza teklatuaren karaktere bat da. Hauek dira readkey funtzioaren ezaugarriak:
  • readkey funtzioak karaktere bat irakurtzeko balio du
  • Teklatua sakatu eta readkey funtzioak teklari dagokion karakterea CHAR datu-motako aldagai batean gordetzen du, hots, readkey funtzioak ez du RETURN beharrik
  • Teklaren karakterea jaso eta gero readkey funtzioak ez du karaktere hori pantailan erakusten
  • readkey funtzioa ez dago konpiladorearen muinean crt unitatean baizik, horregatik crt unitatea erabiliko dela adieraztea derrigorrezkoa da
Ikusi ere keypressed funtzio boolerra. Tekla bat sakatzean keypressed funtzio boolerrak TRUE itzuliko du. Horregatik programa honen bukaeran, exekuzioa gelditzeko ez dugu readln bat erabiltzen eta repeat until keypressed aginduagatik ordezkatu dugu. Programaren exekuzioa bukatzeko return teklan sakatu beharra dago readln jartzean, baina edozein tekla sakatzea nahikoa da repeat until keypressed agindua jartzean. 
program readkey_funtzioa ;
uses
   crt;
var
   cKarak1, cKarak2 : char ;
begin
   clrscr ;
   writeln('Hasteko readln prozedurak karaktere bat') ;
   writeln('nola irakurtzen duen ikus dezagun') ;
   writeln('Lehenengo karakterea eman: ') ;
   readln(cKarak1) ;        (* zein karaktere sartzen ari garen ikusten dugu  *)
                            (* RETURN baten bitartez baieztatu behar dugulako *)

   cKarak1 := lowercase(cKarak1) ;       (* string edo char bat minuskuletara *)
   write('Lehenengo karakterea =====>', cKarak1, '<=====') ;

   writeln ;
   writeln ;
   writeln('readkey funtzioaren txanda, funtzio hau') ;
   writeln('soilik karaktereekin erabil daiteke') ;
   writeln('Bigarren karakterea eman: ') ;
   cKarak2 := readkey ;     (* sarrerako parametrorik ez daukan funtzio baten *)
                            (* deia, funtzioaren emaitza karaktere bat izanik *)

   cKarak2 := lowercase(cKarak2) ;       (* string edo char bat minuskuletara *)
   writeln('Bigarren karakterea =====>', cKarak2, '<=====') ;

   writeln ;
   writeln ;
   writeln ;
   writeln('==============================') ;
   writeln('Edozein tekla sakatu amaitzeko') ;
   writeln('==============================') ;
   
   repeat until keypressed ;
end.

Hona hemen ReadKey_funtzioa izeneko programaren exekuzio baten irudia:

 

5. astea | menu bat (programa nagusian)

Programa batean aukera desberdinak kudeatzeko sarritan menu bat erabiltzen da, eta horrelakoetan aukeraren hautapena karaktere baten bitartez gidatzen da.

Adibidez, jarraian erakusten den Menua1.pas programan eragiketa aritmetikoak egiten dira bi zenbakiekin eta programaren exekuzio bakoitzean cAukera aldagaiaren bitartez eragiketa hautatzen da. Aukera asko direnean azpimarratzekoa da CASE-OF baldintzazko aginduaren komengarritasuna. CASE-OF baldintzazko aginduaren ordez IF-THEN aginduak jari beharko lirateke, baina CASE-OF baldintzazko agindua oso trinkoa eta garbia delako programaren irakurgarritasuna handia izango da.
program AukeraMenuBatezHautatzen_1;
uses
  crt;
var
  cAukera, cItxoin : char;
  rEragigai1, rEragigai2 : real;
begin
   clrscr;
   write('Zenbaki errealekin lan eginez, lehenengo eragigaiaren balioa eman: ');
   readln(rEragigai1);
   write('Zenbaki errealekin lan eginez, bigarren eragigaiaren balioa eman:  ');
   readln(rEragigai2);

   writeln('============Menua============');
   writeln('  +   Batura lortzeko');
   writeln('  -   Kendura lortzeko');
   writeln('  *   Biderkadura lortzeko');
   writeln('  /   Zatiketa burutzeko');
   writeln('=============================');
   write('          Zure aukera: ');
   readln(cAukera);

   case cAukera of
      '+' : writeln(rEragigai1:0:2, ' + ', rEragigai2:0:2, ' = ', rEragigai1+rEragigai2:0:2);
      '-' : writeln(rEragigai1:0:2, ' - ', rEragigai2:0:2, ' = ', rEragigai1-rEragigai2:0:2);
      '*','x','X' : writeln(rEragigai1:0:2, ' * ', rEragigai2:0:2, ' = ', rEragigai1*rEragigai2:0:2);
      '/' : writeln(rEragigai1:0:2, ' / ', rEragigai2:0:2, ' = ', rEragigai1/rEragigai2:0:2);
      else
         writeln('Eragiketa gaizki aukeratuta!');
   end;

   cItxoin := readkey;
   writeln(cItxoin);
end.

Menua1.pas programaren azalpenak:
  • crt unitate bat da eta bere barnean dago readkey funtzioaren kodifikazioa eta clrscr prozeduraren kodifikazioa
  • uses crt bitartez adierazten dugu linker programak nola lan egin behar duen
  • clrscr prozedurak pantaila garbitzen du
  • readkey funtzio bat da eta programan erabili ahal izateko crt unitatea beharrezkoa da, tekla bat sakatzean berari dagokion karakterea
  • cItxoin:=readkey programa gelditzen da tekla bat sakatu arte, tekla bat sakatzean berari dagokion karakterea cItxoin aldagaian gordeko da
  • readkey funtzioari esker cItxoin aldagaian karakteren bat gordetzen da, baina cItxoin aldagaiaren balioa ez da erabiltzen eta konpiladoreak horren abisua ematen du, "warning" hori kentzeko aski da writeln(cItxoin)bat egitea
Menua1.pas programatik abiatuta idatzi Menua2.pas programa, zeinetan programaren exekuzio bakoitzeko eragiketak behin baino gehiagotan egin daitezkeen eta programa bukarazteko aukera berri bat dagoen:
program AukeraMenuBatezHautatzen_2;
uses
   crt;
var
   cAukera, cItxoin : char;
   rEragigai1, rEragigai2 : real;
begin
   repeat
      clrscr;
      writeln('============Menua============');
      writeln('  +   Batura lortzeko');
      writeln('  -   Kendura lortzeko');
      writeln('  *   Biderkadura lortzeko');
      writeln('  /   Zatiketa burutzeko');
      writeln('  A   Programa amaitu');
      writeln('=============================');
      repeat
         write('          Zure aukera: ');
         cAukera := readkey;
         cAukera := upcase(cAukera);
         writeln(cAukera);    (* readkey funtzioak ez du irakurritako tekla erakusten *)
      until (cAukera ='+') or (cAukera ='-') or (cAukera ='*') or (cAukera ='X') or (cAukera ='/') or (cAukera ='A');
      writeln;
      case cAukera of
         '+' : begin
                  write('Zenbaki errealekin lan eginez, lehenengo batugaiaren balioa eman: ');
                  readln(rEragigai1);
                  write('Zenbaki errealekin lan eginez, bigarren batugigaiaren balioa eman: ');
                  readln(rEragigai2);
                  writeln(rEragigai1:0:2, ' + ', rEragigai2:0:2, ' = ', rEragigai1+rEragigai2:0:2);
               end;
         '-' : begin
                  write('Zenbaki errealekin lan eginez, kenkizunaaren balioa eman: ');
                  readln(rEragigai1);
                  write('Zenbaki errealekin lan eginez, kentzailearen balioa eman: ');
                  readln(rEragigai2);
                  writeln(rEragigai1:0:2, ' - ', rEragigai2:0:2, ' = ', rEragigai1-rEragigai2:0:2);
               end;
         '*','X' : begin
                      write('Zenbaki errealekin lan eginez, lehenengo biderkagaiaren balioa eman: ');
                      readln(rEragigai1);
                      write('Zenbaki errealekin lan eginez, bigarren biderkagaiaren balioa eman: ');
                      readln(rEragigai2);
                      writeln(rEragigai1:0:2, ' * ', rEragigai2:0:2, ' = ', rEragigai1*rEragigai2:0:2);
                   end;
         '/' : begin
                  write('Zenbaki errealekin lan eginez, zatikizunaren balioa eman: ');
                  readln(rEragigai1);
                  repeat
                     write('Zenbaki errealekin lan eginez, zatitzailearen balioa eman: ');
                     readln(rEragigai2);
                  until rEragigai2 <> 0.0;
                  writeln(rEragigai1:0:2, ' / ', rEragigai2:0:2, ' = ', rEragigai1/rEragigai2:0:2);
               end;
         'A' : begin
                  writeln('Programatik irtetera goaz!');
               end
      end;

      cItxoin := readkey;         (* emaitzak ikusi ahal izateko itxaron *)
      writeln(cItxoin);           (* konpilazio abisua kentzeko *)
   until cAukera='A';
end.

5. astea | zenbaki edo letra sorta baten maximoa

Zenbaki osoen multzo batean zein da zenbakirik handiena?  

Hainbat zenbaki teklatuaren bitartez irakurri eta guztien artean maximoa zehaztu. Hona hemen algoritmoa:

  1. Zenbakien sorta batekin lan egingo dugu, zenbakien kopurua zehaztu
  2. Sortaren lehen zenbakia irakurri
  3. Lehen zenbaki hori maximoa da
  4. Errepikatu zenbakien sorta amaitu arte:
    • Zenbaki berria irakurri
    • Zenbaki berria orain arteko maximoa baino handiagoa bada maximoaren balioa berritu
  5. Maximoa erakutsi

Demagun iZenbakienKopurua kopuru osoa eta positiboa teklatuaren bitartez irakurriko dela, adibidez 5. Prozesu errepikakor batean 5-1=4 itzuli eman eta itzuliak kontrolatzeko k kontagailua erabili, 5-1=4 itzuliak amaitzean maximoaren balioa pantailaratu. Hau da algoritmotik eratorren taula:

    k        iZbk   
   iMaximoa   
– 8 8
2 11
11
3 4 11
4 23 23
5 17 23


23

Algoritmotik programara jauzi egitean programazio-lengoaiaren elementuak aintzat hartuko dira eta jarraian baliokidean diren bi programa eskaintzen ditugu. Baliokideak izan arren bigarrena hobea da, lehen programak ez baitu algoritmoa zehatz-mehatz jarraitzen.



Programa honek ez du goiko algoritmoa jarraitzen, zenbakiaren irakurketa guztiak prozesu errepikakorraren barruan egiten direlako. Horregatik iMaximoa aldagaiak hasieraketa berezi bat behar du derrigorrez:
{ Maximoaren hasieraketa berezia prozesu errepikakorra baino lehen }

program ZenbakiSortaBatenMaximoa_1 ;

uses
   crt ;
var
   iZenbakiKopurua, iZbk, iZenbatgarrena, iMaximoa, k : integer ;

begin
   clrscr ;
   writeln('Zenbaki positibo osoen sorta batean sartutako maximoa zehaztu') ;
   writeln('-------------------------------------------------------------') ;
   writeln ;
   
   repeat
      write('Zenbaki osoen kopuru eman: ') ;
      readln(iZenbakiKopurua) ;
   until iZenbakiKopurua > 0 ;
   
   iMaximoa := 0 ;     { maximoa bilatzen digulako, hasieraketa baliorik txikiena izan dadila; }
                       { hori dela eta, iMaximoa 0 delako, lehen itzulian iMaximoa aldatuko da }
   for k:=1 to iZenbakiKopurua do
   begin
      repeat
         write(k, '. zenbaki positiboa eman: ') ;
         readln(iZbk) ;
      until iZbk > 0 ;
      
      if iZbk > iMaximoa then      { oraintxe sartutakoa handiagoa denean }
      begin
         iMaximoa := iZbk ;
         iZenbatgarrena := k ;
         writeln('Une honetan, iMaximoa=', iMaximoa, ' eta iZenbatgarrena=', iZenbatgarrena) ;
      end ;
   end ;
   
   writeln ;
   writeln('Maximoa ', iMaximoa, ' izan da eta sortako ', iZenbatgarrena, '. izan da') ;
   
   repeat until keypressed ;
end.



Goiko algoritmoa jarraituz, zenbakiaren lehen irakurketa prozesu errepikakorra baino lehen egiten delako iMaximoa aldagaiak hasieraketa berezerik ez du behar, iMaximoa hasiera iZbk izango delako:
{ Prozesu errepikakorra baino lehen maximoaren hasieraketa: iMaximoa:=iZbk; }

program ZenbakiSortaBatenMaximoa_2 ;

uses
   crt ;
var
   iZenbakiKopurua, iZbk, iZenbatgarrena, iMaximoa, k : integer ;

begin
   clrscr ;
   writeln('Zenbaki positibo osoen sorta batean sartutako maximoa zehaztu') ;
   writeln('-------------------------------------------------------------') ;
   writeln ;
   
   repeat
      write('Zenbaki osoen kopuru eman: ') ;
      readln(iZenbakiKopurua) ;
   until iZenbakiKopurua > 0 ;
   
   repeat
      write('Lehen zenbaki positiboa eman: ') ;
      readln(iZbk) ;
   until iZbk > 0 ;
   
   iMaximoa := iZbk ;              { lehen zenbakia iMaximoa da }
   iZenbatgarrena := 1 ;           { maximoaren posizioa 1 da   }
   for k:=2 to iZenbakiKopurua do
   begin
      repeat
         write(k, '. zenbaki positiboa eman: ') ;
         readln(iZbk) ;
      until iZbk > 0 ;
      
      if iZbk > iMaximoa then      { oraintxe sartutakoa handiagoa denean }
      begin
         iMaximoa := iZbk ;
         iZenbatgarrena := k ;
         writeln('Une honetan, iMaximoa=', iMaximoa, ' eta iZenbatgarrena=', iZenbatgarrena) ;
      end ;
   end ;
   
   writeln ;
   writeln('Maximoa ', iMaximoa, ' izan da eta sortako ', iZenbatgarrena, '. izan da') ;
   
   repeat until keypressed ;
end.


Zenbakiekin lan egin ordez karakterekin lan egingo bagenu, goiko algoritmoak berdin-berdin balio du. Jarraian ematen den programan ikusi larrien alfabetoko minimoa nola lortzen den:
{ Prozesu errepikakorra baino lehen minimoaren hasieraketa: cMinimoa:=cLetra; }

program LetraSortaBatenMinimoa ;

uses
   crt ;
var
   iLetraKopurua, iZenbatgarrena, k : integer ;
   cLetra, cMinimoa : char ;

begin
   clrscr ;
   writeln('Larrien alfabetoko letra sorta batean sartutako minimoa zehaztu') ;
   writeln('---------------------------------------------------------------') ;
   writeln ;
   
   repeat
      write('Zenbat letra sartuko duzu? kopuru osoa eta positiboa eman: ') ;
      readln(iLetraKopurua) ;
   until iLetraKopurua > 0 ;   
   
   repeat
      write('Lehen letra eman: ') ;
      readln(cLetra) ;
      cLetra := upcase(cLetra) ;
   until (cLetra >= 'A') and (cLetra <= 'Z') ;
   
   cMinimoa := cLetra ;             { lehen letra cMinimoa da  }
   iZenbatgarrena := 1 ;            { minimoaren posizioa 1 da }
   for k:=2 to iLetraKopurua do
   begin
      repeat
         write(k, '. letra eman: ') ;
         readln(cLetra) ;
         cLetra := upcase(cLetra) ;
      until (cLetra >= 'A') and (cLetra <= 'Z') ;
      
      if cLetra < cMinimoa then     { oraintxe sartutakoa txikiagoa denean }
      begin
         cMinimoa := cLetra ;
         iZenbatgarrena := k ;
         writeln('Une honetan, cMinimoa=', cMinimoa, ' eta iZenbatgarrena=', iZenbatgarrena) ;
      end ;
   end ;
   
   writeln ;
   writeln('Minimoa ', cMinimoa, ' izan da eta sortako ', iZenbatgarrena, '. izan da') ;
   
   repeat until keypressed ;
end.

Hauxe da programa horren balizko irteera bat:


Programaren aurreko irteeraren taula hauxe da:

   k       cLetra   
   cMinimoa   
– W W
2 K K
3 P K
4 G G
5 H G
6 M G


G