free pascal ošetrenie nezadaného vstupu

Programovacie jazyky, rady, poradňa...
weroro
Flash coder
Flash coder
Používateľov profilový obrázok
Príspevky: 3206
Registrovaný: 14 feb 2009, 22:34
Bydlisko: Bratislava
Kontaktovať používateľa:

free pascal ošetrenie nezadaného vstupu

Príspevok od používateľa weroro »

Ahoj. Mám jednoduchý program, ktorý mi vypíše kópiu zadanej vety toľko krát podľa toho akú hodnotu zadám.

Kód: Vybrať všetko

program kop;
uses Crt;

procedure opakuj;
       var
           s: string;
           i: integer;

       begin
           write('Napíš vetu: ');
           readln(s);
           write('Zadaj počet opakovaní: ');
           readln(i);

           while i > 0 do begin
                writeln(s);
                dec(i);
           end;
       end;

BEGIN
        ClrScr;
        opakuj;
        readln;

END.
Zaujímalo by ma, ako ošetriť vstup, či už textu alebo čísla tak, že ak nebude zadaná textová hodnota program sa ukončí (poprípade vypíše, že nebol zadaný textový vstup) a ak nebude zadané číslo, nech sa automaticky priradí 1.

Chcel som to ošetriť podmienkou, ale nepodarilo sa mi dohľadať, akým spôsobom sa kontroluje nedefinovaný vstup. Skúšal som i = null alebo i = undefined ale hádzalo to chybu. Ak som dal do podmienky if i < 1 then i := 1; tak sa nevykonalo nič a program sa nechcel vypnúť.

Ako sa to prosím robí v pascale? Ešte stále v tom mám chaos.
BX
Addict
Addict
Používateľov profilový obrázok
Príspevky: 4572
Registrovaný: 10 jan 2008, 15:30

Re: free pascal ošetrenie nezadaného vstupu

Príspevok od používateľa BX »

Kód: Vybrať všetko

{$I-}   { disable i/o error checking }
nacitanie vstupu
{$I+}   { enable again i/o error checking - important }
If (IOResult <> 0) then
 begin osetrenie zleho vstupu end;
Dá sa to vraj aj inak, ale ja som to vždy robil takto.
(btw. textová hodnota je zadaná vždy, nie?)
lowmanek
Light Professional
Light Professional
Používateľov profilový obrázok
Príspevky: 977
Registrovaný: 04 apr 2010, 8:53
Bydlisko: 221B Baker Street

Re: free pascal ošetrenie nezadaného vstupu

Príspevok od používateľa lowmanek »

Ano, do stringu sa nacita hodnota vzdy, samozrejme, pokial nieco napises :D
S tymi opakovaniami to bude vyzerat nejak takto:

Kód: Vybrať všetko

const max= 1000;
.
.
{$I-}   
readln(i);
{$I+}   
If (IOResult <> 0) then
begin if (i<0) then  write('Zadane cislo musi byt kladne.')        {Ak bude i zaporne}
          else if (i>max) then write('Zadane cislo musi byt mensie ako ', max, '.');   {Ak bude vacsie ako nejake cislo, ktore zadas ako konstantu na zaciatku programu.}
        i:=1;  
 end;
A namiesto while by som pouzil for, kedze poznas pocet opakovani...ale to je skor chyba krasy
BX
Addict
Addict
Používateľov profilový obrázok
Príspevky: 4572
Registrovaný: 10 jan 2008, 15:30

Re: free pascal ošetrenie nezadaného vstupu

Príspevok od používateľa BX »

On chce kontrolovať, či je premenná naozaj číslom. Ako môžem kontrolovať jej rozsah pomocou IOResult? Tá tvoja sprcha podmienok je blud.
lowmanek
Light Professional
Light Professional
Používateľov profilový obrázok
Príspevky: 977
Registrovaný: 04 apr 2010, 8:53
Bydlisko: 221B Baker Street

Re: free pascal ošetrenie nezadaného vstupu

Príspevok od používateľa lowmanek »

Az teraz som sa na to pozrel blizsie :oops: , len som okopcil to tvoje hladanie chyb, lebo som tam chcel pri chybe zadat 1...Malo to vyzerat takto

Kód: Vybrať všetko

const max= 1000;
.
.
{$I-}   
readln(i);
{$I+}   
If (IOResult <> 0) then
i:=1;  

 if (i<0) then begin write('Zadane cislo musi byt kladne.'); i:=1 end       {Ak bude i zaporne}
          else if (i>max) then begin write('Zadane cislo musi byt mensie ako ', max, '.'); i:=1 end;   {Ak bude vacsie ako nejake cislo, ktore zadas ako konstantu na zaciatku programu.}
weroro
Flash coder
Flash coder
Používateľov profilový obrázok
Príspevky: 3206
Registrovaný: 14 feb 2009, 22:34
Bydlisko: Bratislava
Kontaktovať používateľa:

Re: free pascal ošetrenie nezadaného vstupu

Príspevok od používateľa weroro »

BX napísal:(btw. textová hodnota je zadaná vždy, nie?)
Nie. Ak nebude zadaný textový vstup, tak tam chcem vypísať hlášku, že nebol zadaný vstup a ukončiť program. Len neviem ako to otestovať ak nebude zadaný žiaden vstup. Idem vyskúšať, či nepomôže s = '' (prázdna hodnota)

To stým testovaním čísla, to je čo za psycho? :shock:
lowmanek
Light Professional
Light Professional
Používateľov profilový obrázok
Príspevky: 977
Registrovaný: 04 apr 2010, 8:53
Bydlisko: 221B Baker Street

Re: free pascal ošetrenie nezadaného vstupu

Príspevok od používateľa lowmanek »

Co mas na mysli? {$I-} a {$I+}
Tu to mas dobre vystvetlene... :)
Pod chybou vstupu môžeme rozumieť aj „preklep“, napríklad vložením písmena namiesto číslice
(Error 106: Invalid numeric format.). K vyriešeniu tohto problému treba poznať funkciu IOResult, ktorá po
každej vstupno/vý stupnej operácii nadobúda buď hodnotu 0, ak nedošlo ku chybe, alebo číslo chyby. Keďže
sme zapli v Options – Compiler... prepínač I/O Checking – kontrolu všetkých vstupno/výstupných operácií,
program by hneď skončil s chybovým hlásením. Túto kontrolu však možno vypnúť umiestnením direktívy
{$I - } pred príkaz vstupu a následne ju zapnúť príkazom {$I +}. Schéma má tvar:

Kód: Vybrať všetko

... 
var CHYBA : boolean; 
      X : integer;   { X aký koľvek číselný  typ } 
... 
  begin 
  repeat 
     write('Vlož číslo: '); 
     {$I-} readln(X); {$I+} 
     CHYBA := IOResult <> 0; 
     if CHYBA then writeln('Chyba vstupu!') 
  until not CHYBA; 
  napr. writeln(X) 
.

Ak dôjde ku chybe, IOResult bude rôzny od nuly a preto premenná CHYBA nadobudne hodnotu TRUE. Na
obrazovke sa zobrazí: Chyba vstupu! a znova Vlož číslo:, pretože CHYBA má hodnotu true a negácia (not)
true je false – vtedy sa príkazy v repeat opakujú .

Je to zo skript od Jozefa Pirosku.
weroro
Flash coder
Flash coder
Používateľov profilový obrázok
Príspevky: 3206
Registrovaný: 14 feb 2009, 22:34
Bydlisko: Bratislava
Kontaktovať používateľa:

Re: free pascal ošetrenie nezadaného vstupu

Príspevok od používateľa weroro »

Aha, chápem. Avšak aj tak mi to z nejakého dôvodu nechce priradiť i := 1 ak je IOResult <> 0

Kód: Vybrať všetko

program weroro;
uses Crt;

procedure opakuj;
       var
           s: string;
           i: integer;

       begin

           write('Napíš vetu: ');
           readln(s);
           if s = '' then begin
                ClrScr;
                write('Nebol zadaný textový vstup. Program bude ukončený.');
                Delay(2000);
                exit;
           end;


           write('Zadaj počet opakovaní: ');
           {$I-}
           readln(i);
           {$I+}
           if IOResult <> 0 then

                i := 1; 


           while i > 0 do begin
                writeln(s);
                dec(i);
           end;
       end;

BEGIN
        ClrScr;
        opakuj;
        readln;

END.
Chybu to nehádže pri kompilácii žiadnu, takže tam musím niečo zle riešiť, len neviem čo.
lowmanek
Light Professional
Light Professional
Používateľov profilový obrázok
Príspevky: 977
Registrovaný: 04 apr 2010, 8:53
Bydlisko: 221B Baker Street

Re: free pascal ošetrenie nezadaného vstupu

Príspevok od používateľa lowmanek »

Musis v tom kode pridat za i:=1 aj readln.

Kód: Vybrať všetko

if IOResult <> 0 then begin i:=1; readln end;
Dovod je asi niekde u vyssich sil, ja si to vysvetlit veru neviem :D
BX
Addict
Addict
Používateľov profilový obrázok
Príspevky: 4572
Registrovaný: 10 jan 2008, 15:30

Re: free pascal ošetrenie nezadaného vstupu

Príspevok od používateľa BX »

weroro čo ti vypíše ten program pri zlom vstupe? Buď napíš nejaké príklady, alebo daj exe (na 32b w7 by to mohlo ísť), mne sa kvôli tomu pascal inštalovať nechce.
weroro
Flash coder
Flash coder
Používateľov profilový obrázok
Príspevky: 3206
Registrovaný: 14 feb 2009, 22:34
Bydlisko: Bratislava
Kontaktovať používateľa:

Re: free pascal ošetrenie nezadaného vstupu

Príspevok od používateľa weroro »

O teóriu pascalu som veľmi nezakopol, tak je viac pravdepodobné, že dôvod bude niekde v hornej časti môjho tela. :D

Ale áno, máš pravdu stačilo to tam dopísať. :) Avšak asi som ja zle niečo vysvetlil. Teraz kontroluje nesprávny typ vstupu (keď zadám niečo iné ako číslo. Ja ale potrebujem hlavne ošetriť to, keď vstup zadaný nebude. Proste si to vypýta číslo ale ja aj tak dám enter bez napísania hodnoty. Vtedy to zas nereaguje, nevypíše chybu, ani nič podobné iba môžem v tom okienku enterovať nové riadky do nekonečna, bez toho aby mi niečo vypísalo. Ako sa testuje prázdna hodnota premennej integer? NULL? Undefined? Netuším.

// BX:
w.zip
(25.07 KiB) 17 stiahnutí
BX
Addict
Addict
Používateľov profilový obrázok
Príspevky: 4572
Registrovaný: 10 jan 2008, 15:30

Re: free pascal ošetrenie nezadaného vstupu

Príspevok od používateľa BX »

weroro neviem s tým prázdnym číslom poradiť, takže asi len ak by si načítal nie číslo, ale string a potom si string otestoval na prázdny, príp. prehodil na číslo. Tiež by sa mal dať testovať stdin na EOF, ale to už poradí google.

A ten program už je s tým lowmanekovým vylepšením? Lebo to tam funguje správne, ja som to chcel bez toho - pozrieť sa, prečo by to mohlo tak fungovať.
94jakub
Guru wannabe
Guru wannabe
Používateľov profilový obrázok
Príspevky: 2037
Registrovaný: 15 dec 2006, 13:18
Bydlisko: Martin/BA
Kontaktovať používateľa:

Re: free pascal ošetrenie nezadaného vstupu

Príspevok od používateľa 94jakub »

Skús si to číslo prehodiť do stringu a overiť jeho dĺžku. Plus to celé zabaľ do cyklu(repeat) nech sa to opakuje, kým to bude prázdne.
Napísať odpoveď