Wytlumaczcie mi zasade dzialania - dlaczego tak?

var

  a,b,liczba:Integer;

begin

readln(liczba);

  for a := 1 to liczba do

    begin

    write(a);

      for b := 1 to a do

        begin

        write('*');

        end;

      writeln;

    end;

  readln; 

end.

Mam taki programik wiem co on robi , wiem jak dziala ale nie wiem dlaczego :stuck_out_tongue: Jakby ktos mogl mi opisac krok po kroku … Tzn. program w dzialaniu wyglada tak ze “podaje liczbe np. 5” nastepnie on wyswietla 5 pozycji z gwiazdkami oznaczajacymi ilosc pozycji np. 1 - 1 gwiazdka , 5 -5 gwiazdek itp… tworzy sie z tego taka choinka :slight_smile: A teraz jak ja to widze i moje pytania z komentarzami :

var

  a,b,liczba:Integer; //deklaracja zmiennych to rozumiem - znam podstawy ;)

begin

readln(liczba); // wczytuje liczbe od uzytkownika

  for a := 1 to liczba do // przypisujemy zmiennej a wartosc 1 , program dziala od 1 do liczby podanej przez usera

    begin             

    write(a); // tutaj rozumiem ze program wpisuje wartosc liczbowa od 1 do liczby podanej przez usera

      for b := 1 to a do // tutaj nie rozumiem ! tzn. jest podana nowa zmienna b ale dlaczego do a - a nie do liczby 

        begin // czy nie moglobybyc tam for b := 1 to liczba do  

        write('*');

        end;

      writeln;

    end;

  readln; 

end.

Dodane 24.10.2009 (So) 18:43

Aha i dlaczego program podaje np. dla 2 pozycji dwie gwiazdki a nie np. dla kazdej pozycji po 1 gwiazdce.

Na każdym etapie pierwszej pętli wywołuje następną pętle od 1 do wartości zmiennej a.

Dzięki temu w pierwszym przebiegu pętli zew. masz 1 gwiazdkę, w drugim 2, w 3 3… itd… gdyby było tak jak myślisz że b: 1 do liczba to w każdym rzędzie miał byś po 5 gwiazdek (tzn. tyle ile podał user).

Opis np. dla trzech gwiazdek:

Deklaruje zmienne.

czytam liczbę - 3.

robię pętle od 1 do 3, gdzie aktualna wartość to a (która odpowiada za aktualną ilość gwiazdek do wyświetlenia), a w tej pętli:

robię pętle od 1 do a, za każdym razem wyświetlam jedną gwiazdkę (jeżeli nasze a jest równe np. 2, to pętla wykona się dwa razy)

Koniec :slight_smile:

Mam kolejny problem , pisze sobie taki oto kodzik :

procedure dopisz_do_bazy;

var

plik_tekstowy:text;

napisz:string;

Begin

assign(plik_tekstowy,'C:\bazadanych.txt');

reset(plik_tekstowy);

readln(napisz);

writeln(plik_tekstowy, napisz);

close(plik_tekstowy);

End;

jest to oczywiście fragment kodu - sama procedura ! Ale chodzi mi tutaj o 1 rzecz, mianowicie kiedy uzywam tej procedury i chce cos napisac to on nie zapisuje mi tego do pliku bazadanych.txt - DLACZEGO ?? Natomiast jezeli zmienie linijke :

reset(plik_tekstowy); na rewrite(plik_tekstowy);

to mi zapisuje.

Jednak plik mam utworzony wczesniej na dysku, dlatego uzywam return aby mi nie zamazal zawartosci. Dlaczego wiec nie dziala ta procedura poprawnie ?

Bo reset otwiera plik do odczytu, a rewrite do zapisu (z tym że wymazuje zawartość).

Jeśli chcesz otworzyć plik i czytać oraz zapisywać to musisz zrobić to tak:

AssignFile(f, 'plik.dat');

FileMode := fmOpenReadWrite; // ustawienie praw do odczytu i zapisu

Reset(f);

Seek(f, 0); // przeskok na 0 bajt pliku


BlockWrite, BlockRead...


Close(f);

tylko że to nie ma sensu dla plików tekstowych. Nie da się tak że sobie zmienisz X linię na np: krótsza i ci się reszta przysunie bajtów :wink: Tutaj musisz operować na blokach danych, i dlatego żadne readln, writeln nie ma tutaj zastosowania. Jeśli chcesz robić read/write txt to najlepiej wczytaj cały do TStringList, zmień co potrzebujesz a potem zapisz cały.

list := TStringList.Create;

list.LoadFromFile('plik.txt');

Label1.Caption := list.Strings[8]; // odczyt linii 8

list.Strings[10] := 'Zmieniam linię 10';

list.SaveToFIle('plik.txt');

list.Free;

Pisałem z głowy, może być jakiś mały error ewentualnie :stuck_out_tongue_winking_eye:

Można jeszcze spróbować użyć strumieni (TFileStream), ale to też tylko do binarnych danych, aczkolwiek chyba istnieje klasa dla tekstowych, poszukaj czy jest TTextFileStream albo coś w ten deseń. Chociaż łatwiej będzie Ci użyć TStringList.

Hmm dla mnie to troche wyzsza szkola jazdy bo dopiero sie ucze :wink:

Ale spojrz na cos takiego :

Nieco przerobilem ten kod … ale zapamietuje i przepisuje tylko ostatnia linijke tekstu i dopisuje to co napisze … a ja chcialbym w ten sposob zrobic aby zapamietaj calosc i jeszcze raz przepisal oraz dopisal to co ja dopisze.

bo musisz:

zapamietaj:=slowo1;

wstawić do pętli, czyli przed until eof(…); i najlepiej w ten sposob:

zapamietaj := zapamietaj + #13#10 + slowo1;

Btw. Zdaje się że jest funkcja Append (zamiast Reset, ReWrite) która umożliwia właśnie dopisanie linii do pliku tekstowego. Aczkolwiek ty musisz mieć odczyt też więc tak jako ciekawostkę to mówię.

Btw2. Bardzo nieczytelny ten kod masz :stuck_out_tongue: niby prosty a trudno się go analizuje, żadnych wcięć, i mnóstwo komentarzy które zamiast pomagać przeszkadzają :stuck_out_tongue:

Zamiast: reset(plik_tekstowy);

daj: append(plik_tekstowy);

Będzie dopisywać do końca.

No jezeli wstawie kod

przed petelke end of file , to i tak mi pokaze (zapamieta) ostatnie slowo i przypisze do niego zmienna.

Natomiast wstawiajac to co podales :

wprawdzie zapamietuje niby zawartosc ale tez wyswietla jakies krzaczki a co to jest #13#10 - ten znak ?

Czyli mam rozumiec :

rozwiaze sprawe tzn. jest to zapis na pierwszej z gory pustej linijce ?

Czyli ma to wygladac w ten sposob (jezeli dopisuje cos do juz istniejacego pliku) :

Begin

assign(plik_tekstowy,'C:\bazadanych.txt');

append(plik_tekstowy);

readln(tekst);

writeln(plik_tekstowy,tekst);

Dodane 25.10.2009 (N) 14:00 – OK , wszystko dziala :wink: Wielkie dzieki za pomoc uzylem

procedure dopisz_do_bazy;

var

plik_tekstowy:text;

tekst:string;

Begin

assign(plik_tekstowy,'C:\bazadanych.txt');

append(plik_tekstowy);

writeln;

readln(tekst);

writeln(plik_tekstowy,tekst);

close(plik_tekstowy);

End;

#13#10 to znak nowego wiersza. Właśnie nie jestem pewien jak writeln potem potraktuje taki składaniec, możliwe że się sypnie tak jak mówisz.

writeln tylko dodaje na koniec #13#10, więc w środku a nawet na końcu zapisywanego łańcucha może być taka sekwencja.

Krzaczki prawdopodobnie z innego powodu.