Napriek tomu, že ide o jednu z základných tém, tento článok je napísaný pre skúsených odborníkov. Cieľom je ukázať, aké mylné predstavy bývajú u začiatočníkov v programovaní. Pre praktizujúcich vývojárov sú tieto problémy už dávno vyriešené, zabudnuté alebo si ich vôbec nevšimnú. Článok môže byť užitočný, ak náhodou budete musieť s touto témou niekomu pomôcť. V článku sú vykonané paralely s materiálmi z rôznych kníh o programovaní od autorov Šildta, Stroustrupa a Okulova.
Téma cyklov bola zvolená, pretože na nej vypadáva dosť veľa ľudí pri osvojení si programovania.
Táto metodika je určená pre slabších študentov. Zvyčajne sa silní na tejto téme nezasekávajú a nie sú potrebné žiadne špeciálne metódy pre nich. Druhotným cieľom článku je previesť túto metodiku z triedy „funguje na všetkých študentoch, ale len u jedného učiteľa“ do triedy „funguje u všetkých študentov, všetkých učiteľov“. Na absolútnu originalitu si nenárokujem. Ak už používate podobnú metodiku na učenie tejto témy, prosím napíšte, čím sa váš variant líši. Ak sa rozhodnete aplikovať, podeľte sa so mnou o výsledky, ako to všetko prebehlo. Ak je podobná metodika opísaná v nejakej knihe, prosím napíšte, názov tejto knihy.
Túto metodiku som vypracovával 4 roky, zatiaľ čo som sa individuálne venoval študentom rôznej úrovne prípravy. Celkovo asi päťdesiat študentov a dvetisíc hodín vyučovania. Na začiatku sa študenti na tejto téme večne zasekávali a odchádzali. Po každom študentovi sa metodika a materiály upravovali. Posledný rok už študenti na tejto téme nezasekávajú, tak som sa rozhodol podeliť o tieto poznatky.
Prečo toľko písmen? Cykl je predsa základ!
Ako som už vyššie spomínal, pre praktizujúcich vývojárov a pre silných študentov môže byť zložitosti konceptu cyklov podceňovaná. Napríklad môžete usporiadať dlhú prednášku, vidieť prikyvujúce hlavy a múdre oči. Ale pri pokuse vyriešiť akúkoľvek úlohu nastáva zadržanie a nevysvetliteľné problémy. Po prednáške mali študenti určite len čiastočné porozumenie. Situáciu zhoršuje to, že študenti si sami nemôžu oznámiť, v čom presne spočíva ich mylné presvedčenie.
Raz som si uvedomil, že študenti vnímajú moje príklady ako hieroglyfy. Teda ako nedeliteľné kusy textu, do ktorých je potrebné doplniť nejaké "magické" písmeno a všetko bude fungovať.
Niekedy som si všimol, že študenti si myslia, že na riešenie konkrétneho problému je potrebné nejaké ďalšie konštrukcie, o ktorej som ešte nehovoril. Avšak na riešenie stačilo len trocha modifikovať príklad.
Preto som dospel k myšlienke, že by sa malo zamerať nie na syntax výrazov, ale na myšlienku o refaktoringu opakovaného kódu pomocou cyklov. Akonáhle študenti zvládnu túto myšlienku, akákoľvek syntax sa prinesie s pomocou drobných cvičení.
Komu a prečo učím
Keďže nie sú prijímacie skúšky, na hodinách môžu byť ako silní, tak aj veľmi slabí študenti. Viac o mojich študentoch si môžete prečítať v článku
Snažil som sa, aby programovanie zvládol každý, kto to chce.
Moje hodiny prebiehajú individuálne a študent platí svoje peniaze za každé. Zdalo by sa, že študenti by mali optimalizovať náklady a žiadať minimum. Napriek tomu prichádzajú na osobné hodiny s živým lektorom nie len pre samotné vedomosti, ale pre pocit istoty, že to stihli pochopiť, pocit pokroku a schválenie od experta (lektora). Ak študenti nebudú cítiť pokrok vo svojom vzdelávaní, odídu. Vo všeobecnosti je možné vybudovať hodiny tak, aby študenti cítili pokrok v zvyšovaní počtu známych konštrukcií. Teda najprv podrobne študujeme while, potom sa učíme for, potom do while a máme pripravený kurz na tisíc a jednu noc, v ktorom sa dva mesiace študujú len cykly, a na konci — študent, ktorý na diktát napísal štandardnú knižnicu. Avšak na riešenie praktických úloh je potrebné nielen ovládanie materiálu, ale aj samostatnosť v jeho aplikácii a v hľadaní nových informácií. Preto pre osobné kurzy považujem za správny princíp — naučiť minimum a podporovať samostatné študovanie nuáns a príbuzných tém. V téme o cykloch považujem minimom konštrukciu while. Na nej je možné pochopiť princíp. Znalosť princípu umožňuje samostatne zvládnuť aj for a do-while.
Aby sa slabí študenti naučili materiál, nestačí opísať syntax. Je potrebné ponúknuť množstvo jednoduchých, ale rôznorodých úloh a podrobne vysvetliť príklady. Nakoniec rýchlosť osvojenia závisí od schopnosti študenta transformovať výrazy a vyhľadávať vzory. Pre bystrých študentov budú väčšina úloh nezaujímavé. Pri práci s nimi netreba trvať na riešení 100 % úloh. Môj materiál si môžete pozrieť na . Priznám sa, že repozitár viac pripomína grimár čierneho mága — nikto okrem mňa by nepochopil, čo kde je, a ak zlyháte pri kontrole, môžete sa zblázniť
Metodika je orientovaná na prax
Teória je vysvetlená na príklade riešenia úlohy. Na hodinách základov programovania, kde sa študujú vetvenia a cykly, nebude možné usporiadať užitočnú prednášku na jednu tému na celú hodinu. 15-20 minút stačí na vysvetlenie konceptu. Hlavné ťažkosti sa objavujú pri vykonávaní praktických úloh.
Začiatoční učitelia môžu vyhodiť operátory, vetvenia, cykly a polia za jednu prednášku. Ale študenti sa s problémom osvojenia týchto informácií stretnú.
Nie je totiž dôležité len rozprávať materiál, ale aj uistiť sa, že poslucháči mu rozumejú.
Skutočnosť osvojenia témy sa určuje podľa toho, ako si študent poradí s samostatnou prácou.
Ak sa študentovi podarilo vyriešiť úlohu na tému bez pomoci učiteľa, téma bola osvojená. Aby sa zabezpečila samostatná kontrola, ku každej úlohe je opísaná tabuľka s testovacími scenármi. Úlohy majú jasne vyjadrený poriadok. Nenechávajte úlohy bez riešenia. Ak je aktuálna úloha príliš zložitá, prechádzať na ďalšiu je zbytočné. Je ešte zložitejšia. Aby študent mohol zvládnuť aktuálnu zložitú úlohu, vysvetlí sa mu niekoľko techník na príklade prvej úlohy. Vlastne, celé obsah témy spočíva v technikách prekonávania ťažkostí. Cyklus je skôr vedľajší efekt.
Prvá úloha je vždy príklad. Druhá sa líši len nepatrne a vykonáva sa 'samostatne' hneď po prvej pod dohľadom učiteľa. Všetky nasledujúce úlohy sú zamerané na to, aby upozornili na rôzne drobnosti, ktoré môžu vyvolávať omyly.
Vysvetlenie príkladu predstavuje dialóg, v ktorom študent musí vyvolať spätnú propagáciu a krížovú validáciu, aby sa uistil o osvojení si časti materiálu.
Budem banálny a vyhlásim, že prvý príklad na tému je veľmi dôležitý. Ak existuje materiál na rozsiahlu samostatnú prácu, nedostatky prvého príkladu sa môžu napraviť. Ak okrem príkladu nie je nič, študent pravdepodobne tému neosvojí.
While alebo for?
Jednou z kontroverzných otázok je voľba konštrukcie pre príklad: while alebo for. Raz ma známy praktikujúci vývojár bez učiteľských skúseností presviedčal hodinu, že cyklus for je najjednoduchší na pochopenie. Argumenty sa zameriavali na ‚všetko je jasné a usporiadané‘. Avšak skutočná príčina ťažkostí skutočných začiatočníkov spočíva v samotnej myšlienke cyklu, a nie v jeho písaní. Ak človek nepochopí túto myšlienku, bude mať ťažkosti so syntaxou. Akonáhle je myšlienka pochopená, problémy s formátovaním kódu sa samy vytrácajú.
V mojich materiáloch téma cyklov nasleduje tému o vetvení. Vonkajšia podobnosť if a while umožňuje priamu analógiu: ‚keď je podmienka v hlavičke pravdivá, vykoná sa telo‘. Špeciálnosť cyklu spočíva len v tom, že telo sa vykonáva viackrát.
Môj druhý argument spočíva v tom, že while vyžaduje menej formátovania ako for. Menej formátovania — menej hlúpych chýb s vynechanými čiarkami a zátvorkami. U začiatočníkov ešte nie je dostatočne rozvinutá pozornosť a dôvtip, aby sa automaticky vyhýbali syntaktickým chybám.
Tretí argument — v mnohých dobrých knihách je while vysvetlené ako prvé.
Ak sa študentovi darí ľahko prevádzať výrazy, môže sa o for zmieniť len tak mimochodom. Študent si neskôr sám vyberie, čo mu viac vyhovuje. Ak však prevody spôsobujú ťažkosti, je lepšie neodvádzať pozornosť. Nech najprv študent vyrieši všetko s pomocou while. Keď je téma cyklov zvládnutá, je možné prepisovať riešenia, aby sa precvičila konverzia from while na for.
Cykly s postpodmienkou sú celkom zriedkavý fenomén. Na to vôbec nestrácam čas. Ak študent zvládne myšlienky odhaľovania vzorov a prevodu výrazov, dokáže sa s tým poradiť bez mojej pomoci.
Pri prezentovaní prvého príkladu silným študentom zdôrazňujem, že vo prvom príklade je dôležité zaznamenať nielen riešenie, ale aj celú sekvenciu činností, ktoré viedli k výsledku. Leniví študenti môžu zanedbať písanie a preniesť si len konečný algoritmus. Treba ich presvedčiť, že raz sa im môže naskytnúť zložitá úloha. Na jej riešenie bude potrebné ísť krok za krokom, ako v tomto príklade. Preto je dôležité zaznamenať všetky etapy. V nasledujúcich úlohách bude možné nechať len konečnú verziu riešenia.
Hlavná myšlienka automatizácie spočíva v tom, že počítaču zveríme vykonávanie rutinných úloh namiesto človeka. Jeden zo základných spôsobov je písanie cyklov. Používa sa, keď je v programe za sebou napísaných niekoľko rovnakých opakujúcich sa krokov.
Jasné je lepšie ako nejasné
Môže sa zdať dobrý nápad v prvej úlohe o cykloch vypísať na obrazovku nejakú rovnakú frázu niekoľkokrát. Napríklad:
Hurá, funguje!
Hurá, funguje!
Hurá, funguje!
Hurá, funguje!
Hurá, funguje!
Hurá, funguje!
Hurá, funguje!
Hurá, funguje!
Takáto verzia je zlá v tom, že na výstupe nie je vidieť hodnotu čítača. To je problém pre začiatočníkov. Nenechávajte ho bez povšimnutia. Spočiatku bola táto úloha prvá a úloha o vypisovaní čísel v rastúcom poradí bola druhá. Musel som zavádzať dodatočné výrazy "cyklus N-krát" a "cyklus od A do B", ktoré sú v podstate to isté. Aby som nevytváral zbytočné entity, rozhodol som sa ukázať len príklad s vypisovaním číselnej sekvencie. Nie každému sa podarí bez prípravy naučiť sa udržať v hlave čítač a modelovať správanie programu v hlave. Niektorí študenti sa prvýkrát stretávajú s modelovaním "v hlave" práve na téme o cykloch.
Po určitom cvičení dávam úlohu na opakovanie rovnakého textu na samostatné riešenie. Ak najskôr poskytujeme viditeľný čítač a potom neviditeľný, študenti majú menej problémov. Niekedy stačí nápoveda "nepíš čítač na obrazovku".
Ako to vysvetľujú ostatní?
Väčšina vzdelávacích materiálov na internete predkladá syntax cyklu ako súčasť "prednášky". Napríklad na developer.mozilla.org (v súčasnosti) sa spolu s cyklom while opisuje aj niekoľko ďalších konštrukcií. Predkladajú sa iba samotné konštrukcie vo forme šablón. Výsledok ich spustenia je popísaný slovami, pričom ilustrácia chýba. Podľa môjho názoru takýto spôsob podania témy znižuje užitočnosť týchto materiálov na nulu. Študent môže prepísať kód a spustiť ho sám, avšak referenčný bod na porovnanie je predsa len potrebný. Ako pochopiť, že príklad bol správne prepísaný, ak nemáme s čím porovnať výsledok?
Keď sa predloží iba šablóna, bez príkladu, študentovi sa to stáva ešte zložitejším. Ako pochopiť, že fragmenty kódu sú v šablóne správne rozmiestnené? Môže sa pokúsiť napísať nejako, a potom to spustiť. Ale ak neexistuje referenčný bod na porovnanie výsledku, tak spustenie tiež nepomôže.
V kurze C++ na Intuit sa syntax cyklu nachádza na tretej strane prednášky 4 na tému „operátory“. Pri vysvetľovaní syntaxe cyklov sa osobitne zdôrazňuje pojem „operátor“. Pojem je podávaný ako súbor faktov ako „symbol; to je operátor“, "{} to je zložený operátor", „telo cyklu musí byť operátorom“. Tento prístup sa mi nepáči, pretože akoby skrýval dôležité súvislosti za jedným pojmom. Rozbor zdrojového kódu programu na termíny na takejto úrovni potrebujú vývojári kompilátorov na implementáciu špecifikácie jazyka, ale rozhodne nie študenti na prvom stupni. Začiatočníci v programovaní zriedka majú dostatočnú dôvtipnosť, aby sa tak starostlivo zaoberali termínmi. Zriedkavý človek si zapamätá a pochopí nové slová na prvý pokus. Prakticky nikto nedokáže správne aplikovať termín, ktorý práve poznal. Preto u študentov vzniká množstvo chýb ako „napísal while(a<7);{, a program nefunguje“.
Podľa môjho názoru je lepšie na začiatku poskytnúť syntax konštrukcie hneď so zátvorkami. Variant bez zátvoriek vysvetľovať iba ak žiak položí konkrétnu otázku „prečo tu bez zátvoriek a funguje“.
V knihe Okulova „Základy programovania“ z roku 2012 sa zoznámenie s cyklami začína vzorom for, následne sú uvedené odporúčania na jeho využitie a potom nasleduje experimentálny oddiel vyučovania. Rozumiem, že kniha bola napísaná pre tú menšinu veľmi nadaných študentov, ktorí sa zriedkavo dostávajú na moje prednášky.
V populárnych knihách sa vždy uvádza výsledok úryvkov kódu. Napríklad u Schildta „Java 8. Kompletný sprievodca“ z roku 2015. Najskôr je uvedený vzor, potom príklad programu a hneď po ňom — výsledok vykonania.
Ako príklad zvážme cyklus while, v ktorom sa vykonáva spätný
odpočet, začínajúci od 10, a vypíše sa presne 10 riadkov „taktov“://Продемонстрировать применение оператора цикла while class While { public static void main(String args []) { int n = 10; while (n > 0) { System.out.println("такт " + n); n--; } } }Po spustení tento program vypíše desať „taktov“ nasledujúcim spôsobom:
takt 10
takt 9
takt 8
takt 7
takt 6
takt 5
takt 4
takt 3
takt 2
takt 1
Prístup s popisom vzoru, príkladu programu a výsledku práce tohoto programu sa používa aj v knihe „JavaScript pre deti“ a v kurze js na w3schools.com. Formát webovej stránky dokonca umožňuje, aby bol tento príklad interaktívny.
V knihe Stroustrupa „Princípy a prax s využitím C++“ z roku 2016 autor šiel ešte ďalej. Najprv sa vysvetľuje, aký výsledok by mal vzniknúť, a až potom sa ukazuje text programu. A pritom ako príklad nie je použitý len tak náhodný program, ale je uvedený pohľad do histórie. To pomáha upriamiť pozornosť na neho „Pozri, to nie je len nejaký bezvýznamný text. Vidíš niečo významné.“
Ako príklad iterácie zvážme prvý program vykonaný na stroji so skladovaným programom (EDSAC). Napísal ho David Wheeler v počítačovej laboratórii Katedry informatiky na Cambridgeskej univerzite (Cambridge University, England) 6. mája 1949. Tento program počíta a tlačí jednoduchý zoznam štvorcov.
0 0
1 1
2 4
3 9
4 16
...
98 9604
99 9801
Tu je v každom riadku číslo, za ktorým nasleduje znak tabulácie (‘t’) a štvorec tohto čísla. Verzia tohto programu v jazyku C++ vyzerá takto://Вычисляем и распечатываем таблицу квадратов чисел 0-99 int main() { int i = 0; // Начинаем с нуля while(i < 100){ cout << i << 't' << square(i) << 'n'; ++i; } }
Zaujímavé je, že vzor syntaktickej štruktúry v tejto knihe nie je popísaný. Stroustrup v učiteľskom sprievodcovi () kladie dôraz na to, že si váži inteligenciu svojich študentov. Možno je schopnosť identifikovať vzor v niekoľkých príkladoch považovaná za prejav takej inteligencie.
Ako vysvetľujem ja sám
Prístup Stroustrupa: popis výsledku, následné riešenie úlohy a potom samostatná analýza študentom — sa zdá byť najpremyslenejší. Preto som sa rozhodol brať za základ práve jeho prístup, ale sa rozprávať na menej historickom príklade — úlohe výstupu «obsahu». Vytvára rozpoznateľný maják, aby sme mohli neskôr povedať „spomeň si na úlohu o obsahu“ a aby si študenti presne na ňu spomenuli. Vo svojom príklade som sa snažil upozorniť ešte na dve z najbežnejších mylných predstáv. Ďalej o nich napíšem podrobnejšie.
Na tejto úlohe sa zoznamujeme s technikami riešenia zložitých problémov. Počiatočné riešenie by malo byť primitívne a jednoduché. A potom sa môžeme zamyslieť, ako to riešenie vylepšiť.
Úvod
Kapitola 1
Kapitola 2
Kapitola 3
Kapitola 4
Hlava 5
Kapitola 6
Kapitola 7
Záver
Podľa mojich pozorovaní prístup «šablóna-príklad-výsledok» v rôznych kombináciách nakoniec vedie k tomu, že študenti vnímajú cyklus ako hieroglyf. To sa prejavovalo v tom, že nerozumeli, prečo tam písať podmienku, ako si vybrať medzi i++ a i— a iné zdanlivo očividné veci. Aby sme predišli týmto mylným predstavám, prístup k rozprávanie o cykloch by mal zdôrazniť zmysel opakovania rovnakých činností a až potom — ich formovanie pomocou konštrukcie. Preto predtým, ako dáme syntax cyklu, je potrebné vyriešiť úlohu „tvárou v tvár“. Primitívne riešenie úlohy o obsahu vyzerá takto:
Console.WriteLine("Úvod");
Console.WriteLine("Kapitola 1");
Console.WriteLine("Kapitola 2");
Console.WriteLine("Kapitola 3");
Console.WriteLine("Kapitola 4");
Console.WriteLine("Kapitola 5");
Console.WriteLine("Kapitola 6");
Console.WriteLine("Kapitola 7");
Console.WriteLine("Záver");
Ako ho môžeme vylepšiť?
Nahradiť monotónne činnosti cyklom.
Aké činnosti sa tu opakujú za sebou bez zmeny?
V tomto fragmente také nie sú. Avšak príkazy na výstup slova „Kapitola“ s číslom sú veľmi podobné jeden druhému.
Preto ďalší krok — hľadanie rozdielov medzi fragmentmi. V tejto úlohe je to jasné, neskôr sa budú opakovať nie jednotlivé príkazy, ale bloky kódu so 5 riadkami a viac. Hľadať bude potrebné nie len v zozname príkazov, ale aj v konštrukciách vetvenia alebo cyklu.
V príklade je rozdiel medzi príkazmi v číslach po slove „Kapitola“.
Akonáhle je rozdiel nájdený, je potrebné pochopiť zákonitosti zmeny. Rozlišujúci fragment je toto číslo? Neustále sa zvyšuje alebo znižuje? Ako sa mení hodnota čísla medzi dvoma príkazmi vedľa seba?
V príklade číslo za slovom „Hlava“ sa zvyšuje skokom 1. Rozdiel je nájdený, vzorec odhalený. Teraz môžeme nahradiť odlišný fragment premennou.
Takúto premennú je potrebné deklarovať pred prvým z opakujúcich sa fragmentov. Takúto premennú zvyčajne nazývajú I alebo j alebo nejakým rozšíreným názvom. Jej počiatočná hodnota by mala byť rovná prvému hodnotenému výstupnému číslu. V príklade je prvé číslo 1.
Akú počiatočnú hodnotu je potrebné zvoliť pre výstup číselného radu „100, 101, 102, 103, 104, 105“?
V tomto rade je prvé číslo 100.
Po každej príkaze výstupu je potrebné zvýšiť hodnotu tejto premennej o 1. Tento prírastok je krok zmeny.
Aký krok bude v rade čísel „100, 102, 104, 106“?
V tomto rade je krok 2.
Po nahradení odlišného fragmentu premennou bude kód vyzerať takto:
Console.WriteLine("Úvod");
int i;
i = 0;
Console.WriteLine("Hlava " + i);
i = i + 1;
Console.WriteLine("Hlava " + i);
i = i + 1;
Console.WriteLine("Hlava " + i);
i = i + 1;
Console.WriteLine("Hlava " + i);
i = i + 1;
Console.WriteLine("Hlava " + i);
i = i + 1;
Console.WriteLine("Hlava " + i);
i = i + 1;
Console.WriteLine("Hlava " + i);
i = i + 1;
Console.WriteLine("Záver");
Po aplikácii techniky „vyjadriť vzorec pomocou premennej“ sa v kóde objaví niekoľko skupín rovnakých akcií, ktoré nasledujú za sebou. Teraz je možné nahradiť opakované akcie cyklom.
Sekvencia riešenia úlohy, v ktorej je potrebné použiť cykly, pozostáva z týchto krokov:
- Riešiť „priamo“ množstvom jednotlivých príkazov
- Nájsť vzorec
- Vyjadriť vzorec pomocou premennej
- Formulovať vo forme cyklu
Ďalej sa zavádzajú nové pojmy, aby sa študent ocitol v situácii „všetko chápem, ale neviem povedať“:
— čítač — vždy premenná, ktorá je potrebná na sledovanie počtu krokov cyklu. Zvyčajne celé číslo, ktoré sa porovnáva s obmedzením.
— krok čítača — popis vzoru zmeny čítača.
— obmedzenie — číslo alebo premenná, s ktorou sa čítač porovnáva, aby bol algoritmus konečný. Hodnota čítača sa mení tak, aby sa blížila k obmedzeniu.
— telo cyklu — súbor príkazov, ktoré sa budou opakovať. Keď sa hovorí „príkaz napísaný v tele cyklu“, myslí sa práve na telo.
— iterácia cyklu — jednorázové vykonanie tela cyklu.
— podmienka cyklu — logický výraz, od ktorého závisí, či sa vykoná ďalšia iterácia. (Tu môže dôjsť k zámene s vetvovými konštrukciami)
Treba byť pripravený na to, že v prvých fázach študenti budú používať termíny nesprávne. To platí pre silných aj slabých. Upevnenie spoločného jazyka je celé umenie. Teraz to napíšem stručne: treba si stanoviť úlohu 'vyber fragment kódu s <termín>' a sám správne používať tieto termíny v rozhovore.
Po transformácii s cyklom dostaneme fragment:
Console.WriteLine("Úvod");
int i = 0;
while (i < 7) {
Console.WriteLine("Kapitola " + i);
i = i + 1;
}
Console.WriteLine("Záver");Hlavná mylná predstava
Jedno populárne omyl študentov spočíva v tom, že do konštrukcie cyklu umiestňujú také činnosti, ktoré je potrebné urobiť len raz. Napríklad takto:
;
int i = 0;
while (i < 7) {
Console.WriteLine("Úvod")
Console.WriteLine("Kapitola " + i);
i = i + 1;
Console.WriteLine("Záver");
}
Študenti sa neustále stretávajú s týmto problémom, ako na začiatku, tak aj pri zložitejších úlohách.
Kľúčová rada v tomto prípade:
Koľkokrát je treba opakovať napísanie príkazu: raz alebo mnohokrát?
Príkazy na výstup slov "Úvod" a "Záver", ako aj deklarácia a inicializácia premennej i sa nelíšia od ostatných opakovaných akcií. Vykonávajú sa iba raz, preto ich treba napísať mimo tela cyklu.
V kóde musia zostať všetky tri etapy riešenia, aby sa na ne neskôr dalo odvolávať v prípade ťažkostí. Prvé dve varianty stačí okomentovať, aby neprekážali.
Pozornosť študenta treba upriamiť na nasledujúce skutočnosti:
— Vo vyjadrení cyklu sa zvyčajne porovnáva čítač a obmedzenie. Čítač sa môže zmeniť v tele cyklu, zatiaľ čo obmedzenie — nie. Na porušenie tohto pravidla je potrebné navrhnúť presvedčivé dôvody.
— Príkazy na výstup slov "Úvod" a "Záver" sú mimo telá cyklu. Musíme ich vykonať 1-krát. "Úvod" — pred opakovaním činností, "Záver" — po.
V procese upevňovania tejto témy, osvojenia nasledujúcich, ako aj pri riešení problémov je aj silným študentom užitočné položiť otázku: „A toto opatrenie, koľkokrát je treba vykonať? Raz alebo veľakrát?“
Rozvoj ďalších zručností
V procese štúdia cyklov si študenti stále trénujú zručnosť diagnostiky a riešenia problémov. Na vykonanie diagnostiky si musí študent predstaviť želaný výsledok a porovnať ho s aktuálnym výsledkom. Od rozdielu medzi nimi závisia akcie potrebné na nápravu.
Keďže študenti v tejto fáze ešte len ťažko predstavujú „želaný“ výsledok, môžu sa orientovať na testovacie údaje. Zvyčajne nikto na tejto úrovni ešte nechápe, čo sa môže pokaziť a ako s tým bojovať. Preto zapisujem do zošita opis typických problémov a niekoľko spôsobov ich riešenia. Výber najvhodnejšieho z nich je úlohou samotného študenta.
Záznam je potrebný, aby sa dalo opýtať: „Dosiahli sme to, čo sme očakávali?“, „Ktorá z týchto situácií sa vykonala?“, „Pomohlo uplatnené riešenie?“
- Počet akcií je o 1 menej alebo viac, než sa očakáva. Spôsoby riešenia:
— zvýšiť počiatočnú hodnotu počítadla o 1.
— nahradiť prísny operátor porovnania () na neprísny (=).
— zmeniť hodnotu obmedzenia o 1. - Akcie v cykle sa uskutočňujú nepretržite, do nekonečna. Spôsoby riešenia:
— pridať príkaz na zmenu počítadla, ak chýba.
— opraviť príkaz na zmenu počítadla tak, aby sa jeho hodnota priblížila k obmedzeniu.
— odstrániť príkaz na zmenu obmedzenia, ak je v tele cyklu. - Počet akcií v cykle je o viac než 1 menej alebo viac, než sa očakávalo. Akcia v cykle sa nevykonala ani raz. Najprv je potrebné zistiť aktuálne hodnoty premenných tesne pred začiatkom cyklu. Spôsoby riešenia:
— zmeniť počiatočnú hodnotu obmedzenia
— zmeniť počiatočnú hodnotu počítadla
Obvykle je problém 3 spojený s použitím nesprávnej premennej alebo s ne-inicializovaním počítadla.
Po tomto vysvetlení môžu mať študenti stále rôzne omyly o fungovaní cyklov.
Aby som rozptýlil najčastejšie, dávam úlohy:
- Kde je obmedzenie, počiatočná hodnota počítadla alebo krok počítadla zadané používateľom.
- Kde je potrebné použiť hodnotu počítadla v nejakom aritmetickom výraze. Ideálne so počítadlom v podčitateľnom výraze alebo v menovateli, aby bola rozlíšenie nelinerárne.
- Kde sa hodnota čítačky nezobrazuje na obrazovke počas behu cyklu. Napríklad na výstup potrebného počtu identických fragmentov textu alebo na nakreslenie figúry pomocou želvovej grafiky.
- Kde je potrebné najprv vykonať jedny opakujúce sa úkony a potom iné.
- Kde je potrebné vykonať iné úkony pred a po opakujúcich sa.
Pre každú úlohu je potrebné poskytnúť testovacie dáta a očakávaný výsledok.
Aby sme pochopili, akou rýchlosťou môžeme postúpiť, je potrebné dať prečítať podmienky týchto úloh a opýtať sa: „Čím sa líšia od príkladu?“, „Čo je potrebné zmeniť v príklade, aby sa vyriešili?“. Ak študent rozumne odpovedá, nech vyrieši aspoň jednu na hodine, ostatné nech rieši doma samostatne. Ak bude riešenie úspešné, môžeme začať vysvetlenie podmienok vo vnútri cyklov.
Ak sú s samostatným riešením ťažkosti, je potrebné všetko precvičiť na hodine. Aby riešenie úlohy nepripomínalo kreslenie sovy, odporúčam najskôr vyriešiť úlohu nie univerzálne. Teda tak, aby riešenie prešlo prvým testom a nepoužívalo konštrukciu cyklu. Až potom aplikovať transformácie na dosiahnutie univerzálnosti riešenia.
Cyklus a vetvenia
Podľa môjho názoru je užitočné poskytnúť tému „cykly vo vnoreniach“ osobitne. Tak, aby bolo neskôr viditeľné, aký je rozdiel medzi opakovaným overením podmienky a jednorazovým.
Úlohy na upevnenie budú o výstupe čísel od A do B, ktoré zadáva používateľ:
— vždy v rastúcom poradí.
— v rastúcom alebo klesajúcom poradí v závislosti od hodnôt A a B.
K téme „vetvenia vo vnoreniach“ je potrebné prejsť až potom, čo študent ovládol techniky: „nahradenie zákonitosti premennou“ a „nahradenie opakujúcich sa činností cyklom“.
Hlavný dôvod na použitie vetvení vo vnoreniach je anomálie v zákonitosti. Uprostred je potlačená v závislosti od vstupných dát.
Študenti, ktorí sú schopní hľadať riešenie kombinovaním jednoduchých techník, potrebujú len povedať „vetvenia je možné písať vo vnoreniach“ a dať úlohu „pre príklad“ úplne na samostatné riešenie.
Úloha na príklad:
Používateľ zadá číslo X. Zobraziť v stĺpci čísla od 0 do 9 a umiestniť znak ‘+’ pred to číslo, ktoré sa rovná X.
Ak bolo zadané 00+
1
2
3
4
5
6
7
8
9
Ak bolo zadané 60
1
2
3
4
5
6+
7
8
9
Ak bolo zadané 90
1
2
3
4
5
6
7
8
9+
Ak bolo zadané 7770
1
2
3
4
5
6
7
8
9
Ak krátke vysvetlenie nestačí na napísanie cyklu, potom je potrebné dosiahnuť univerzálne riešenie tej istej úlohy bez cyklu.
Bude to jedna z dvoch možností:
Želaný
string temp;
temp = Console.ReadLine();
int x;
x = int.Parse(temp);
if (x==0) {
Console.WriteLine(0 + "+");
} else {
Console.WriteLine(0);
}
if (x==1) {
Console.WriteLine(1 + "+");
} else {
Console.WriteLine(1);
}
if (x==2) {
Console.WriteLine(2 + "+");
} else {
Console.WriteLine(2);
}
if (x==3) {
Console.WriteLine(3 + "+");
} else {
Console.WriteLine(3);
}
if (x==4) {
Console.WriteLine(4 + "+");
} else {
Console.WriteLine(4);
}
if (x==5) {
Console.WriteLine(5 + "+");
} else {
Console.WriteLine(5);
}
if (x==6) {
Console.WriteLine(6 + "+");
} else {
Console.WriteLine(6);
}
if (x==7) {
Console.WriteLine(7 + "+");
} else {
Console.WriteLine(7);
}
if (x==8) {
Console.WriteLine(8 + "+");
} else {
Console.WriteLine(8);
}
if (x==9) {
Console.WriteLine(9 + "+");
} else {
Console.WriteLine(9);
}
Možný
string temp;
temp = Console.ReadLine();
int x;
x = int.Parse(temp);
if (x==0) {
Console.WriteLine("0+n1n2n3n4n5n6n7n8n9");
}
if (x==1) {
Console.WriteLine("0n1+n2n3n4n5n6n7n8n9");
}
if (x==2) {
Console.WriteLine("0n1n2+n3n4n5n6n7n8n9");
}
if (x==3) {
Console.WriteLine("0n1n2n3+n4n5n6n7n8n9");
}
if (x==4) {
Console.WriteLine("0n1n2n3n4+n5n6n7n8n9");
}
if (x==5) {
Console.WriteLine("0n1n2n3n4n5+n6n7n8n9");
}
if (x==6) {
Console.WriteLine("0n1n2n3n4n5n6+n7n8n9");
}
if (x==7) {
Console.WriteLine("0n1n2n3n4n5n6n7+n8n9");
}
if (x==8) {
Console.WriteLine("0n1n2n3n4n5n6n7n8+n9");
}
if (x==9) {
Console.WriteLine("0n1n2n3n4n5n6n7n8n9+");
}
Podobnú úlohu dávam vopred počas štúdia témy o vetvení.
Ak študent dosiahne „možný“ variant, je potrebné povedať, že existuje mnoho riešení tej istej úlohy. Rozlišujú sa však odolnosťou voči zmenám požiadaviek. Položte otázku: „Koľko miest v kóde bude potrebné opraviť, ak bude potrebné pridať ďalšie číslo?“ V „možnom“ variante bude potrebné pridať ešte jedno vetvenie a dopísať nové číslo v 10 ďalších miestach. V „želanom“ variante stačí pridať iba jedno vetvenie.
Zadajte úlohu reprodukovať „želaný“ variant, potom nájdite v kóde pravidelnosť, vykonajte zámenu premennej a napíšte cyklus.
Ak máte nápad, ako vyriešiť túto úlohu bez cyklu nejakým iným spôsobom, prosím napíšte v komentároch.
Cykly vo vnútri cyklov
V tejto téme je dôležité poznamenať, že:
— počítadlá pre vnútorný a vonkajší cyklus musia byť rôznymi premennými.
— počítadlo pre vnútorný cyklus je potrebné nulovať mnohokrát (t.j. v tele vonkajšieho cyklu).
V úlohách výstupu textu nie je možné najprv napísať jedno písmeno na niekoľkých riadkoch a potom druhé. Je potrebné najprv vypísať všetky písmená prvého riadku, potom všetky písmená druhého a tak ďalej.
Vysvetlenie témy o cykloch v cykloch je najlepšie začať s vysvetlením dôležitosti nulovania počítadla.
Úloha na príklad:
Používateľ zadá dve čísla: R a T. Vypísať dve riadky symbolov "#". V prvom riadku by malo byť R kusov symbolov. V druhom riadku T kusov. Ak bude niektoré číslo negatívne, vypísať hlásenie o chybe.
R=5, T=11#####
###########
R=20, T=3####################
###
R=-1, T=6Hodnota R musí byť nezáporná
R=6, T=-2Hodnota T musí byť nezáporná
Je zrejmé, že táto úloha má tiež minimálne dva spôsoby riešenia.
Želaný
string temp;
int R;
int T;
temp = Console.ReadLine();
R = int.Parse(temp);
temp = Console.ReadLine();
T = int.Parse(temp);
int i = 0;
while (i < R)
{
Console.Write("#");
i = i + 1;
}
Console.WriteLine();
i = 0;
while (i < T)
{
Console.Write("#");
i = i + 1;
}
Možný č. 1
string temp;
int R;
int T;
temp = Console.ReadLine();
R = int.Parse(temp);
temp = Console.ReadLine();
T = int.Parse(temp);
int i = 0;
while (i < R)
{
Console.Write("#");
i = i + 1;
}
Console.WriteLine();
int j = 0;
j = 0;
while (j < T)
{
Console.Write("#");
j = j + 1;
}
Rozdiel je v tom, že v "možnom" riešení pre výstup druhého riadku bola použitá druhá premenná. Je potrebné naliehať na používanie tej istej premennej pre oba cykly. Tento obmedzenie môžeme odôvodniť tým, že riešenie s jedným čítačom pre dva cykly bude ilustráciou pojmu "nulovanie čítača". Pochopenie tohto pojmu je potrebné pri riešení nasledujúcich úloh. Ako kompromis môžeme uchovať obe riešenia úlohy.
Typický problém s použitím jednej premennej-čítača pre dva cykly sa prejavuje takto:
R=5, T=11#####
######
Počet symbolov v druhom riadku nezhoduje s hodnotou T. Ak potrebujete pomoc s týmto problémom, mali by ste "ťuknúť na nos" v poznámkach o typických problémoch s cyklami. Toto je symptóm č. 3. Diagnostikuje sa, ak pridáte výstup hodnoty počítadla priamo pred druhý cyklus. Opravené nulovaním. Ale to by sa lepšie nemalo hneď hovoriť. Študent by mal skúsiť formulovať aspoň jednu hypotézu.
Samozrejme, je tu aj taká varianta riešenia. Ale ja som ju u študentov nikdy nevidel. V etape učenia cyklov by rozprávanie o ňom rozptyľovalo pozornosť. K tomu sa môžeme vrátiť neskôr, pri štúdiu funkcií práce so stringami.
Možný č. 2
string temp;
int R;
int T;
temp = Console.ReadLine();
R = int.Parse(temp);
temp = Console.ReadLine();
T = int.Parse(temp);
Console.WriteLine(new String('#', R));
Console.WriteLine(new String('#', T));
Ďalšia povinná úloha:
Na obrazovku vypíšte čísla od 0 do 9. Každé číslo by malo byť na svojom riadku. Počet čísiel na riadku (W) sa zadáva z klávesnice.
W=10
1
2
3
4
5
6
7
8
9
W=100000000000
1111111111
2222222222
3333333333
4444444444
5555555555
6666666666
7777777777
8888888888
9999999999
Ak študent zvládol techniku nahrádzania premennej, mal by to zvládnuť celkom rýchlo. Možný problém opäť spočíva v nulovaní premennej. Ak si nevie poradiť s transformáciou, znamená to, že ste sa ponáhľali a mali by ste riešiť jednoduchšie úlohy.
Ďakujem za pozornosť. Dajte like a prihláste sa na kanál.
P.S. Ak ste našli preklepy alebo chyby v texte, prosím, dajte mi vedieť. Môžete to urobiť označením časti textu a stlačením na Mac „⌘ + Enter“, a na klasických klávesniciach „Ctrl / Enter“, alebo cez súkromné správy. Ak tieto možnosti nie sú k dispozícii, napíšte o chybách v komentároch. Ďakujem!
Len registrovaní používatelia sa môžu zúčastniť prieskumu. , prosím.
Prieskum pre čitateľov bez karmy
20,0%Učím profesionálne, +12
10,0%Učím profesionálne, -11
70,0%Neučím, +17
0,0%Neučím, -10
0,0%Iné0
Hlasovalo 10 používateľov. Zdržalo sa 5 používateľov.
Zdroj: habr.com
