WP - egzaminu pisemnego omówienie niektórych zadań

by NOWIESZ

Spis zadań

[ spis ]

Zestaw VI / zadanie 9

Zestaw IV / zadanie 9

[ spis ]

Zestaw VI / zadanie 10

:-)

[ spis ]

Zestaw VII / zadanie 1

Zestaw II / zadanie 4

[ spis ]

Zestaw VII / zadanie 2

Rekord składa się z dwóch pól stałych (a typu Integer oraz b typu Boolean). Składa się także z pól wariantowych - w zależności od wariantu, z dwóch pól, obu typu Real lub dwóch pól, z których jedno jest Real, a drugie Char.
Zmieniając wiersz {*} zmienia się jedynie to, że liczba pól stałych zmniejsza się o 1.

[ spis ]

Zestaw VII / zadanie 3

Zestaw II / zadanie 6

[ spis ]

Zestaw VII / zadanie 4

Zestaw II / zadanie 7

[ spis ]

Zestaw VII / zadanie 5

Zestaw II / zadanie 3

[ spis ]

Zestaw VII / zadanie 6

Zestaw III / zadanie 6

[ spis ]

Zestaw VII / zadanie 7

Procedura może wyglądać następująco:

  procedure Odwroc(n: Integer);
  var We: TextFile;
      Wy: file of Integer;
      Liczby: array of Integer;
      i: Integer;

  begin
    SetLength(Liczby,n);
    AssignFile(We,'LICZBY.TXT');
    ReSet(We);
    for i:=0 to n-1 do
      ReadLn(We,Liczby[i]);
    CloseFile(We);
    AssignFile(Wy,'ODWR.INT');
    ReWrite(Wy);
    for i:=n-1 downto 0 do
      Write(Wy,Liczby[i]);

    CloseFile(Wy);
    Liczby:=nil;
  end;

Użycie tablicy dynamicznej Liczby nie powinno być konieczne, ale to zrobiłem jakby ktoś był jednak tym zainteresowany. Chyba można przyjąć, że jest już zadeklarowana jakaś tablica o odpowiedniej wielkości. Reszta chyba nie wymaga wyjaśnień.

[ spis ]

Zestaw VII / zadanie 8

Strona 424/425.

[ spis ]

Zestaw VII / zadanie 9

Strona 208.
Ale warto zaznaczyć, że stan-wyjątkowy to nie jest po prostu nazwa stanu wyjątkowego, ale obiekt odpowiedniego typu lub konstruktor tego obiektu (częściej używane) - patrz przykład 7.13 ze str.209.

[ spis ]

Zestaw VII / zadanie 10

Zestaw I / zadanie 3

[ spis ]

Zestaw VIII / zadanie 1

Strona 77/78.

[ spis ]

Zestaw VIII / zadanie 2

Strona 123.
Ale wątpie, żeby to się pojawiło, bo teraz używa się typu klasowego (str.113), co dhAM często i dobitnie zaznaczał.

[ spis ]

Zestaw VIII / zadanie 3

Strona 164.
Wystarczy zapamiętać, że shl i shr działają wyłącznie na liczbach całkowitych (przesuwają bity). Pozostałe działają na typie Boolean oraz na typach całkowitych (po bitach jak na typie logicznym).

[ spis ]

Zestaw VIII / zadanie 4

Zestaw I / zadanie 7

[ spis ]

Zestaw VIII / zadanie 5

Odpowiedź na podobne pytanie, ale rozszerzone o parametry przekazywane przez stałe i różnice między nimi znajdziecie pod Zestaw III / zadanie 9

[ spis ]

Zestaw VIII / zadanie 6

Zestaw I / zadanie 8

[ spis ]

Zestaw VIII / zadanie 7

Podobny przykład 12.2/2 ze strony 350.
Konstrukcja wyrażenie:długość:miejsca_dzies ma na celu sformatowanie liczby.
Gdy nie ma podanego parametru miejsca_dzies (albo jest ujemny) to używany jest format zmiennoprzecinkowy (ten śmieszny z E). Wtedy długość oznacza ile co najmniej miejsc ma zajmować cała liczba (dodawane są ewentualnie spacje na początku). Ale ten format składa się koniecznie z minimum dziesięciu znaków (- lub spacja cyfra.cyfry_dzies E znak 4_cyfry_wykł), więc jeśli długość<=10 to jest ona po prostu ignorowana.
Gdy podane są miejsca_dzies to rezygnuje się z formatu z E i wypisuje się liczbę tak jakbyśmy my ją napisali, ale do określonego miejsca po przecinku (ewentualnie zaokrąglając). Jeśli chodzi o dłguość to będzie miała ona takie samo znaczenie (ale teraz ma sens by była mniejsza niż 10).

  1. -1.2E+0001
  2. __-12 (znak '_' oznacza spację)
  3. -1.2E+0001
  4. -12.34500000000000000000 (jest 17 zer, ale pod koniec mogą wyjść bzdury)

[ spis ]

Zestaw VIII / zadanie 8

Przykład 13.19 ze strony 441.
Funkcja Ord dla liczb całkowitych zwraca jej wartość (niezależnie czy jest pełnego typu, czy okrojonego). Dla znaków, zwraca ich kod ASCII (też nieważne czy pełny, czy okrojony). Jeśli chodzi o typ Boolean to zwraca 1 dla TRUE i 0 dla FALSE. Natomiast dla wartości typu wyliczeniowego zwraca jej liczbę porządkową, czyli numer w definicji tegoż typu (licząc od 0).

  1. 30
  2. 1
  3. 30
  4. 2

[ spis ]

Zestaw VIII / zadanie 9

Zestaw VII / zadanie 8

[ spis ]

Zestaw VIII / zadanie 10

Odpowiedź na podobne pytanie, ale rozszerzone o rodzaje metod znajdziecie pod Zestaw IV / zadanie 10

[ spis ]

Zestaw IX / zadanie 1

Odpowiedź na podobne pytanie, ale rozszerzone o dyrektywy języka znajdziecie pod Zestaw III / zadanie 2

[ spis ]

Zestaw IX / zadanie 2

Odpowiedź na podobne pytanie, ale rozszerzone o typy rzeczywiste znajdziecie pod Zestaw III / zadanie 3

[ spis ]

Zestaw IX / zadanie 3

Strona 151.

[ spis ]

Zestaw IX / zadanie 4

Zestaw II / zadanie 7

[ spis ]

Zestaw IX / zadanie 5

Odpowiedź na podobne pytanie, ale rozszerzone o parametry przekazywane przez wartość i różnice między nimi znajdziecie pod Zestaw III / zadanie 9

[ spis ]

Zestaw IX / zadanie 6

Zestaw III / zadanie 6

[ spis ]

Zestaw IX / zadanie 7

Przykład 12.1/1 ze strony 344.
Oczywiście do zmiennej i wczytana jest wartość 1, a do r 2. Po wczytaniu tych liczb "wskaźnik" pliku ustawia się na spacji po dwójce, więc wcztanym znakiem do znak jest ' ' (gdybyśmy chcieli wczytać liczbę to wskaźnik pliku przeskoczyłby spacje aż trafiłby na liczbę). Później do lancuch zostanie wczytany 'matematyka'.

[ spis ]

Zestaw IX / zadanie 8

Podobny przykład 13.35 ze strony 455.
Myślę, że nie musicie się przejmować tym gadaniem o wyłączonym koprocesorze, bo w OP jest to chyba niewykonalne.
Formatowanie liczby w procedurze Str polega na tym samym jak przy Write (patrz: Zestaw VIII / zadanie 7), tyle że wynik trafia do zmiennej łańcuchowej zamiast na ekran oraz przetworzony łańcuch jest skracany (po prostu obcięty na końcu) do długości tej zmiennej łańcuchowej.

  1. ' 12'
  2. '-1.2E+'
  3. '-1.2E+0001'
  4. '-1.2E+00'

Warto jeszcze zauważyć, że ostatnie 3 przykłady dałyby dokładnie ten sam wynik gdyby zmienne łańcuchowe były odpowiednio długie (ale nie są więc są w różnych miejscach obcięte). Tak jest dlatego, że miejsca_dzies nigdzie nie są podane (raz jest ujemne, co na jedno wychodzi), a długość jest <=10, czyli traktowana wtedy jak 10.

[ spis ]

Zestaw IX / zadanie 9

Strona 413 oraz przykład 13.11/1 ze strony 414.
Lista jednokierunkowa i stos to właściwie to samo, ale z założenia w stosie dostępny jest jedynie jego wierzchołek (nie przegląda się innych elementów oraz można dodawać i usuwać wyłącznie z jego szczytu).

[ spis ]

Zestaw IX / zadanie 10

Strona 303.
Obiekt polimorficzny to obiekt, w którym metody pokrywają metody z obiektów nadrzędnych (str.76).

[ spis ]

Zestaw X / zadanie 1

Odpowiedź na podobne pytanie, ale rozszerzone o słowa kluczowe znajdziecie pod Zestaw III / zadanie 2

[ spis ]

Zestaw X / zadanie 2

Zestaw V / zadanie 1

[ spis ]

Zestaw X / zadanie 3

Strona 186/187.

[ spis ]

Zestaw X / zadanie 4

Zestaw III / zadanie 7

[ spis ]

Zestaw X / zadanie 5

Zestaw I / zadanie 9

[ spis ]

Zestaw X / zadanie 6

Zestaw III / zadanie 6

[ spis ]

Zestaw X / zadanie 7

Przykład 12.10/1 (ten drugi program) ze strony 367.
Wszystko było by dobrze, gdyby nie to, że trzecia linijka nie zawiera 'o' na początku, ale za to spację na końcu.
Pierwsza pętla wczytuje 28 znaków (zatrzymuje się na spacji, której nie wczyta). Eoln zwraca FALSE, bo jesteśmy na spacji, a nie na końcu linii. Linia Read(tekst,znak,znak,znak); wczytuje tą spację oraz 2 znaki CR i LF (i ignoruje je). Następna pętla wczytuje 31 znaków. Mimo, że zatrzyma się na spcaji, to funkcją SeekEoln przeskoczymy na znak końca linii (bo ta funkcja dąży do końca linii omijając spacje i taby oraz zwraca TRUE jesli dojdzie). Następna linia Read(tekst,znak,znak,znak); wczyta już znaki CR, LF i pierwszy znak z następnej linii, które zignoruje. Następna pętla wczyta 37 znaków (ze spacją na końcu włącznie), które wypisze. Funkcja Eof oczywiście zwaraca FALSE (bo nie jesteśmy na końcu pliku). Później funkcja SeekEof, przechodzi do końca pliku (omijając spacje, taby i znaki końca linii) i zwraca TRUE jeśli dojdzie (a w tym przypadku dojdzie).

[ spis ]

Zestaw X / zadanie 8

  1. TRUE , FALSE
  2. #255 , #0
  3. 255 , 0
  4. 127 , -128
  5. TRUE , FALSE
Wyjaśnienie działania funkcji High i Low (szczególnie dla tablic) możecie znaleźć pod Zestaw II / zadanie 10.

[ spis ]

Zestaw X / zadanie 9

Zestaw V / zadanie 9

[ spis ]

Zestaw X / zadanie 10

Zadanie jest chyba przeterminowane.

[ spis ]

Zestaw XI / zadanie 1

Podobny przykład 4.3/4 ze strony 98.
Typ q definiuje wartości całkowite z przedziału [-40;0].
Jeśli chodzi o typ p, to jego definicja jest błędna, ponieważ przy definicji typu okrojonego pierwsze wyrażenie stałe nie może zaczynać się od nawiasu (bo wtedy oczekiwana jest definicja typu wyliczeniowego).

[ spis ]

Zestaw XI / zadanie 2

  program MinSingle;
  {$APPTYPE CONSOLE}
  var p,x: Single;
  
  begin
    p:=1; x:=p/2;
    while x<>0 do
    begin
      p:=x; x:=p/2;
    end;
    WriteLn('Najmniejsza wartosc dodatnia w typie Single: ',p);
    ReadLn;
  end.

Działa to dlatego, że liczby zapisane są w systemie dwójkowym, więc najmniejsza wartość w typie Single powinna być pewną ujemną potęgą dwójki.

[ spis ]

Zestaw XI / zadanie 3

Zestaw I / zadanie 3

[ spis ]

Zestaw XI / zadanie 4

Pakiet jest to zbiór skompilowanych modułów. Ich zastosowanie polega na tym, że można wymienić pewną część programu, zamiast całości.
Ogólna postać pakietu wygląda następująco:

  package nazwa_pakietu;
    requires nazwy_innych_pakietów;
    contains lista_nazw_modułów;
  end.

[ spis ]

Zestaw XI / zadanie 5

Podstawowe (te niezależne od procesora i systemu operacyjnego): ShortInt (8-bitowy ze znakiem), Byte (8-bitowy bez znaku), SmallInt (16-bit. ze zn.), Word (16-bit. bez zn.), LongInt (32-bit. ze zn.), LongWord (32-bit. bez zn.), Int64 (64-bit. ze zn.).
Ogólne (zależne od procesora lub systemu operacyjnego): Integer (aktualnie 32-bit. ze zn.), Cardinal (aktualnie 32-bit. bez zn.).

[ spis ]

Zestaw XI / zadanie 6

Zestaw I / zadanie 6

[ spis ]

Zestaw XI / zadanie 7

Strona 127.

[ spis ]

Zestaw XI / zadanie 8

Zestaw I / zadanie 8

[ spis ]

Zestaw XI / zadanie 9

Linijki kodu:

  1. Wyjaśniać nie muszę.
  2. Następuje przepisanie zawartości tablicy ts1 do tablicy ts2 (też chyba oczywiste).
  3. Następuje zarezerwowanie pamięci na 1 element tablicy dynamicznej oraz przypisanie do zmiennej td1 wskaźnika na tą zarezerwowaną pamięć.
  4. Też oczywiste.
  5. Następuje przypisanie zmiennej td2 wskaźnika ze zmiennej td1 (w odróżnieniu od tablic statycznych, gdzie odbywa się przepisanie zawartości tablicy). Od tej pory zmienne td1 i td2 będą działały na tym samym obszarze pamięci, czyli elementy tych tablic będą identyczne oraz wykonanie jakiejść operacji na jednej jest równoznaczne z równoczesnym wykonaniem identycznej operacji na drugiej.
  6. Przypisanie wartości do elementu tablicy td2, ale co za tym idzie także do td1.
Dlatego po wykonaniu kodu zmienne będą miały następujące wartości:

[ spis ]

Zestaw XI / zadanie 10

a:=VarArrayCreate([0,3,1,5],varDouble);

[ spis ]

Zestaw XII / zadanie 1

  program MinDouble;
  {$APPTYPE CONSOLE}
  var p,x: Double;
  
  begin
    p:=1; x:=p/2;
    while x<>0 do
    begin
      p:=x; x:=p/2;
    end;
    WriteLn('Najmniejsza wartosc dodatnia w typie Double: ',p);
    ReadLn;
  end.

Działa to dlatego, że liczby zapisane są w systemie dwójkowym, więc najmniejsza wartość w typie Double powinna być pewną ujemną potęgą dwójki.

[ spis ]

Zestaw XII / zadanie 2

Zestaw II / zadanie 2

[ spis ]

Zestaw XII / zadanie 3

Zestaw II / zadanie 3

[ spis ]

Zestaw XII / zadanie 4

Właściwie to nie mam zielonego pojęcia. Można pewnie znaleźć coś na ten temat w suplemencie do ŻK (którego nie posiadam).

[ spis ]

Zestaw XII / zadanie 5

???????????????

[ spis ]

Zestaw XII / zadanie 6

Zestaw II / zadanie 6

[ spis ]

Zestaw XII / zadanie 7

Zestaw II / zadanie 7

[ spis ]

Zestaw XII / zadanie 8

Zestaw II / zadanie 8

[ spis ]

Zestaw XII / zadanie 9

  1. (td1=td2)=FALSE ponieważ w zmiennych td1 i td2 przechowywane są wskaźniki na tablice dynamiczne (a te wskaźniki są różne, bo tablice są w różnych miejscach w pamięci).
  2. (td1[0]=td2[0])=TRUE ponieważ tutaj porównywane są elementy tablic, które w wyniku wcześniejszych przypisań mają takie same wartości.

[ spis ]

Zestaw XII / zadanie 10

  function f(n: Integer): Integer;
  var sum: Integer;
      i: Integer;
  
  begin
    if (n=1)or(n=2) then
      sum:=1
    else
      try
        sum:=0;
        for i:=1 to n-1 do
          Inc(sum,f(i));
      except
        on EIntOverflow do
          sum:=-1;
      end;
    f:=sum;
  end;

Na skutek wystąpienia warunku EIntOverflow moja funkcja zwróci wartość -1, czyli taką, której normalnie nigdy by nie osiągnęła (ale nie wiem czy o to chodziło dhAM). Można zamiast tego kazać wypisać jakiś komunikat o błędzie.

[ spis ]

Zestaw XIII / zadanie 1

  program MinExtended;
  {$APPTYPE CONSOLE}
  var p,x: Extended;
  
  begin
    p:=1; x:=p/2;
    while x<>0 do
    begin
      p:=x; x:=p/2;
    end;
    WriteLn('Najmniejsza wartosc dodatnia w typie Extended: ',p);
    ReadLn;
  end.

Działa to dlatego, że liczby zapisane są w systemie dwójkowym, więc najmniejsza wartość w typie Extended powinna być pewną ujemną potęgą dwójki.

[ spis ]

Zestaw XIII / zadanie 2

W pierwszym przypadku mamy do czynienia z literałem zmiennym, czyli tak jakby stałą określonego typu. Można jej jednak przypisywać nowe wartości, choć nie jest to wskazane i wykonywalne jedynie przy dyrektywie kompilatora $J+.
W drugim przypadku mamy do czynienia po prostu ze zmienną, która ma zainicjalowaną wartość.

[ spis ]

Zestaw XIII / zadanie 3

Łańcuchy zasobowe to są łańcuchy, które są jakby łańcuchami stałymi, ale pamiętane są w zewnętrznym pliku, który można podmienić (np. zmieniając wersję językową programu).
Deklaruje się je tak:

  resourcestring identyfikator= wyrażenie_łańcuchowe_stałe;

Dalej w programie łańuch jest traktowany jak zadeklarowany przy użyciu klauzuli const. Różnica jest taka, że przy kompilacji programu łańcuch jest zapisywany do pliku .DRC i to właśnie zawartość tego pliku (a nie ciąg znaków z definicji) decyduje o tym co jest widziane pod identyfikatorem identyfikator.
Tak przynajmniej brzmi oficjalna wersja, bo ja nie zaobserwowałem faktu pojawienia się pliku .DCR, natomiast łańuchy zasobowe, znalazły się wśród wielu zasobów wewnątrz pliku .EXE.

[ spis ]

Zestaw XIII / zadanie 4

Zestaw III / zadanie 4

[ spis ]

Zestaw XIII / zadanie 5

Podstawowe (te niezależne od procesora i systemu operacyjnego): Real48 (6 bajtowy), Single (4 bajty), Double (8 bajtów), Extended (10 bajtów), Comp (8 bajtów), Currency (8 bajtów). Przy czym te ostatnie dwa są stałoprzecinkowe.
Ogólne (zależne od procesora lub systemu operacyjnego): tylko Real (aktualnie 8 bajtów).

[ spis ]

Zestaw XIII / zadanie 6

Zestaw III / zadanie 6

[ spis ]

Zestaw XIII / zadanie 7

Zestaw III / zadanie 7

[ spis ]

Zestaw XIII / zadanie 8

Należy użyć tak zwanego przeciążania funkcji, czyli napisać dwie funkcje o identycznej nazwie i różnych parametrach. Zależnie parametrów aktualnych kompilator sam zadecyduje, którą funkcję wywołać.

  function Suma(s1,s2,s3: Integer): Integer; overload;
  begin
    Suma:=s1+s2+s3;
  end;

  function Suma(s1,s2,s3: Real): Real; overload;
  begin
    Suma:=s1+s2+s3;
  end;

[ spis ]

Zestaw XIII / zadanie 9

Sytuacja wygląda następująco. Zmienna r jest w rzeczywistości wskaźnikiem na tablicę dynamiczną, która tak naprawdę jest tablicą wskaźników na kolejne tablice dynamiczne elementów typu Extended.
Sama zmienna r zajmuje 4 bajty (bo to wskaźnik przecież).
Po wykonaniu pierwszej linijki zostanie pamięć zarezerwowana na 20 elementów, które są też wskaźnikami (na kolejne tablice dynamiczne). Zajmują one 20*4=80 bajtów pamięci.
Tablica r ma elementy od 0 do 19, więc Low(r)=0 i High(r)=19 zatem pętla for wykona się dla elementów i równych od 0 do 19. Po jej wykonaniu zostanie zarezerwowana pamięć na tablice dynamiczne, które mają kolejno 20, 19, ..., 2, 1 elementów (razem 210) typu Extended. Czyli zajmuje 210*10=2100 bajtów pamięci.
Teraz powstaje pytanie o co tak naprawdę chodziło dhAM?
Jeśli chodziło mu o to ile łącznie zajmują elementy typu Extended to odpowiedź jest 2100. Jednak właściwie to tablica r jest tablicą wskaźników (co z tego, że wskazują one na kolejne tablice dynamiczne), a wtedy odpowiedzią jest 80. A może chodziło o całość pamięci zużytą przez wszystkie części tablicy - wtedy należy odpowiedzieć 4+80+2100=2184.
Żeby zwolnić pamięć należałoby dla każdego elementu tablicy r, a później dla samej tablicy r wykonać procedurę Finilize ze wskaźnikiem podanym jako parametr.

  for i:=Low(r) to High(r) do
    Finalize(r[i],0);
  Finalize(r,0);

[ spis ]

Zestaw XIII / zadanie 10

Przykład 8.11 ze strony 253.
divcplx(z,s,z);

[ spis ]
[ powrót ] [ mail w sprawie odpowiedzi z WP ]