Strona główna » Poradniki » Logomocja » LOGIA » Logia 2000/01 - Etap II
 

Logia 2000/01 - Etap II

· Etap I · Etap II · Etap III ·
iOryginalna treść zadań jest dostępna pod oficjalnym adresem konkursu LOGIA

Zadanie 1

Zdefiniuj polecenie ENTLIK :n :bk rysowania "entlików", tzn łamanych, takich jak na poniższym rysunku. Pierwsza dana procedury :n określa stopień złożoności entlika, a druga :bk (bok kratki) długość najkrótszego boku tej łamanej. Żółw powinien zaczynać kreślenie entlika z miejsca, w którym stoi i w kierunku, w którym patrzy, a kończyć na drugim końcu. Pozycje żółwia: początkowa i końcowa na rysunku najbardziej złożonego entlika są zaznaczone kolorem zielonym (start) i czerwonym (koniec).

Obrazek 1 do zadania 1

Strategia

Istnieje wiele poprawnych rozwiązań tego zadania. Przedstawione, przykładowe rozwiązanie obrało startegię na wyszczególnieniu powtarzających się elementów. W ten sposób kod jest prostszy, ale może nie być zby czytelny.

Element

Jak można zauważyć większość rysunku składa się z elementu, który reprezentują 3 odcinki, których kolejne długości to a, 3a, a. Odcinki leżą do siebie pod kątem prostym. Funkcja realizuje taki element wygląda następująco:

  1. oto ENTLIK_ln :bk
  2.   np :bk
  3.   pw 90
  4.   np :bk*3
  5.   pw 90
  6.   np :bk
  7. już

Rysowanie całości

Pierwszy etap polega na przesunięciu rysunku na środek ekranu.

  1. oto ENTLIK :n :bk
  2.   pod
  3.   niech "el 1
  4.   jeśli (:n >= 2) [niech "el :el + 2]
  5.   powtórz (:n - 2) [niech "el :el + 4]
  6.   ws :bk*:el/2 pw 90
  7.   ws :bk*(:el+0.5) lw 90
  8.   opu

(3. - 5.) Oblicz ile odcinków wzwyż zostanie narysowane. Warto zauważyć, że dla :n = 1 odcinków wysokości jest h, dla :n = 2, 4h, a potem dla każdego :n powyżej dwóch wysokość zwiększa się o 4h. Na podstawie wyliczonej ilości elementów: (6. - 7.) przesuwamy żółwia w lewy dolny róg rysunku (pozycja zielonej strzałki).

  1.   powtórz (:n - 2) [
  2.     powtórz 2 [
  3.       ENTLIK_ln :bk
  4.       pw 90
  5.     ]
  6.     lw 90
  7.     np :bk
  8.     powtórz 4 [
  9.       ENTLIK_ln :bk
  10.       pw 90
  11.     ]
  12.     lw 90
  13.     np :bk
  14.   ]

Zarówno po lewej jak i po prawej stronie powtarzającym elementem dla złożoności :n conajmniej 2 jest element złożony z połowy obrazka złozoności 2 i element złożony z 5 kwadratów. Tego typu obiekt można narysować (16. - 19.) rysując cztery razy wyszczególniony element ENTLIK_ln.

  1.   jeśli (:n > 1) [
  2.     powtórz 2 [
  3.       ENTLIK_ln :bk
  4.       pw 90
  5.     ]
  6.     lw 90
  7.     ws :bk
  8.     lw 90
  9.     ws :bk
  10.   ]

Kolejny etap rysowania polega na narysowaniu połowy obrazka złożoności :n = 2.

  1.   ENTLIK_ln :bk

Stałym elementem, który zawsze jest rysowany jest element położony najwyżej na obrazku. Rysowanie drugiej części odbywa się identycznie co pierwsza. Jedynie wyszczególniene etapy rysowania są rysowane w odwrotnej kolejności i obracanie żółwia odbywa się w drugą stronę.

  1.   jeśli (:n > 1) [
  2.     ws :bk
  3.     lw 90
  4.     ws :bk
  5.     powtórz 2 [
  6.       ENTLIK_ln :bk
  7.       pw 90
  8.     ]
  9.   ]
  10.   powtórz (:n - 2) [
  11.     lw 90
  12.     np :bk
  13.     powtórz 4 [
  14.       ENTLIK_ln :bk
  15.       pw 90
  16.     ]
  17.     lw 90
  18.     np :bk
  19.     powtórz 2 [
  20.       ENTLIK_ln :bk
  21.       pw 90
  22.     ]
  23.   ]
  24.   lw 90
  25. już

Zadanie 2

Zdefiniuj polecenie PENTLIK, którego skutkiem będzie narysowanie na środku ekranu możliwie dużego znaku graficznego, takiego jak na rysunku poniżej.

Obrazek 1 do zadania 2

Strategia

PENTLIK jest szczególnym przypadkiem zadania 3 i procedury ENTLIK o złożoności 2, dlatego nie ma potrzeby pisania oddzielnej funkcji. Oczywiście warto spróbować napisać procedurę PENTLIK, aby zrozumieć schemat rysowania.

Zadanie 3

Zdefiniuj polecenie z jednym parametrem ENTPENT :n, które dla danej liczby 2, spowoduje narysowanie na środku ekranu możliwie dużego znaku graficznego, takiego jak na rysunku w zadaniu 2, dla :n = 3, takiego jak na rysunku poniżej, a dla innych wartości n - podobnych, odpowiednio mniej lub bardziej złożonych znaków.

Obrazek 1 do zadania 3

Strategia

Warto zauważyć, że elementem, który jest rysowany wiele razy składa się z kwadratu pośrodku i czterech wzorków złożonych z 5 elementów każdy. Procedura ENTPENT_kwadrat ma za zadanie narysować kwadrat w o środku w pozycji żółwia, a ENTPENT_wzor rysuje kolejne kwadraty na kolejnych warstwach.

Zadanie sprowadza się do napisania funkcji rekurencyjnej, która narysuje kwadrat pośrodku aktualnego obszaru, a następnie obszar podzieli na 4 równe ćwiartki i w każdej z nich rozpocznie procedurę od nowa. Warunkiem zakończenie może być fakt, że wyznaczony obszar jest mniejszy od pola rysowanego kwadratu. Prościej jest sprawdzać ile warstw kwadratów jest jeszcze do narysowania przekazując przy wywołaniu rekurencyjnym wartość :n zmniejszaną przy każdym kolejnym wywołaniu. Wtedy, gdy :n osiągnie 0 to należy zakończyć cykl rekurencji.

Rysowanie kwadratu

Poniższy kod rysuje kwadrat o boku :a o środku w pozycji XY żółwia.

  1. oto ENTPENT_kwadrat :a
  2.   pod
  3.   ws :a/2 pw 90
  4.   ws :a/2 lw 90
  5.   opu
  6.   powtórz 4 [
  7.     np :a
  8.     pw 90
  9.   ]
  10.   pod
  11.   np :a/2 pw 90
  12.   np :a/2 lw 90
  13.   opu
  14. już

Rekurencja

Poniższa funkcja rysuje kolejne wartwy kwadratów.

  1. oto ENTPENT_wzor :n :a
  2.   ENTPENT_kwadrat :a
  3.   pod
  4.   ws :a*(potega 2 (:n - 1)) pw 90
  5.   ws :a*(potega 2 (:n - 1)) lw 90
  6.   opu
  7.   jeśli (:n > 0) [
  8.     powtórz 4 [
  9.       ENTPENT_wzor :n-1 :a
  10.       pod
  11.       np :a*2*(potega 2 (:n - 1))
  12.       pw 90
  13.       opu
  14.     ]
  15.   ]
  16.   pod
  17.   np :a*(potega 2 (:n - 1)) pw 90
  18.   np :a*(potega 2 (:n - 1)) lw 90
  19.   opu
  20. już

(1.) Narysuj kwadrat pośrodku obszaru. (2. - 5.) Przesuń do lewej, dolnej ćwiartki. (6. - 14.) Jeśli pozostały do narysowania kolejne warstwy to wywołaj ENTPENT_wzor w każdej ćwiartce rysunku. (15. - 18.) Wróć do pozycji wyjściowej w danym obszarze.

Główna funkcja

Główna funkcja ustala rozmiary obrazka, rysuje tło i rozpoczyna rekurencję z odpowiednimi argumentami.

  1. oto ENTPENT :n
  2.   niech "h 460
  3.   niech "a :h/((potega 2 :n+1) + 1)
  4.   pod
  5.   ws :h/2 pw 90
  6.   ws :h/2 lw 90
  7.   opu
  8.   wielokąt [
  9.     ukm "niebieski3
  10.     powtórz 4 [
  11.       np :h
  12.       pw 90
  13.     ]
  14.   ]
  15.   wróć
  16.   ukp "żółty
  17.   ugp 2
  18.   ENTPENT_wzor :n :a
  19.   ukp "czarny
  20.   ugp 1
  21. już

Oblicz (2.) szerokość najmniejszego kwadratu na podstawie (1.) ustalonej wysokości. Należy pamiętać o uwzględnieniu marginesu! (tj. :n + 1 zamiast :n) (3. - 6.) Przejdź do lewego, dolnego rogu tła. (7. - 13.) Narysuj tło i (14.) wróć. (15. - 16.) Ustal styl pisaka. (17.) Narysuj rekurencyjnie wzór. (18. - 19.) Przywróć domyślne ustawienia pisaka.