LINUXSOFT.cz Přeskoč levou lištu
Uživatel: Heslo:  
   CZUKPL

> Perl (69) - Projekt - online přenos

Perl Dnes dokončíme projekt, jehož obsahem bylo vytvořit uživatelsky přívětivou čtečku sportovních výsledků pro příkazový řádek.

6.6.2008 07:00 | Jiří Václavík | Články autora | přečteno 11656×

Dnes máme za úkol dokončit práce na projektu. Chybí nám napsat poslední věc a tou je online přenos.

Online přenos

Načrtněme si opět předběžný postup.

  • Abychom mohli spustit online přenos, musíme nejprve vybrat právě jeden zápas. Až pokud se to úspěšně podaří, můžeme pokračovat dále.
  • Vybraný zapas vytiskneme pomocí funkce tiskni_vyhovujici.
  • Na základě ligy a čísla zápasu určíme zápas.
  • Nyní budeme periodicky volat metodu prenos a na jejím základě aktualizovat zobrazená data.
  • Na závěr zobrazíme konečný výsledek

Pojďme se do toho pustit. Bude třeba napsat tuto podmínku, kterou jsme nechali minule neimplementovanou.

if($online){
    #implementace online přenosu
}

Předně musíme ze všech zápasů vybrat pouze jediný. K tomu si napíšeme zvlášť podprogram.

    @vyhovujici = vyber_zapas(@vyhovujici);

To je v podstatě opakované volání metody najdi_zapas_podle_kriterii, která na základě kritérií postupně zužuje výběr. Jakmile klesne na jediný zápas, můžeme výběr ukončit a postupovat dále.

sub vyber_zapas {
    my @vyhovujici = @_;
    while(scalar @vyhovujici > 1){
        print "Byly nalezeny zapasy (".scalar @vyhovujici."):\n";
        tiskni_vyhovujici(@vyhovujici);
        print "Musite zadat zpresnujici kriterium: ";
        my $kriteria;
        chomp($kriteria = <STDIN>);
        my @kriteria = split(" ", $kriteria);
        @vsechna_kriteria = (@vsechna_kriteria, @kriteria);
        @vyhovujici = $live->najdi_zapas_podle_kriterii(\@vyhovujici, \@kriteria);
    }
    return @vyhovujici;
}

Je ovšem možné, že doplňující kritérium vyloučí všechny zápasy. V takovém případě musíme program ukončit, protože nemáme jak pokračovat. Jinou možností by bylo nebrat poslední kritérium v úvahu.

   die "Zadny vyhovujici zapas\n" if scalar @vyhovujici == 0;

Nyní zjistíme ligu a číslo zápasu, které je třeba předat metodě prenos. Ale je třeba si dát pozor na tuto věc: Číslo zápasu a liga (parametry odkaz_idzapasu a odkaz_liga v hashi s informacemi o zápase) nemusí být vůbec dostupné - resp. nejsou dostupné, pokud zatím v zápase nedošlo ke sledované události. Nastává zde tedy problém. Jak můžeme získat data, když nevíme odkud? Tuto otázku nemá smysl řešit - tato data nezískáme, protože neexistují.

Vyřešíme to trochu jinak a to tak, že si počkáme, až budou dostupná. To znamená průběžně kontrolovat, zda nenastala událost a neobjevil se nám odkaz na seznam událostí. Jakmile událost nastane, získáme odkaz a budeme ji moci zobrazit. Bude to sice o něco náročnější na programování, ale v zásadě tím nic neztrácíme.

Periodicky tak budeme stahovat informace o zápasech. Vždy v nich najdeme ten náš zápas, který sledujeme. Ten nyní může být ve čtyřech stavech.

  • hraje se a nejsou dostupné detailní informace (nedošlo k události)
  • hraje se a už jsou dostupné detailní informace (došlo k události)
  • zápas byl ukončen
  • zápas je před výkopem

Je-li zápas před výkopem, budeme v intervalech zjišťovat, zda to stále platí, dokud se nezačne hrát. Když se začne hrát, nejsou zpravidla dostupné žádné události. Proto budeme v intervalech tisknout pouze probíhající minutu. Jakmile ale dojde k události, vyskočíme z cyklu, protože v tomto okamžiku budeme schopni stáhnout podrobnosti k zápasu - již známe odkaz (prvky odkaz_idzapasu a odkaz_liga). Pokud zápas skončil, ukončíme cyklus také. Pokud tyto požadavky zahrneme do další části programu, získáme toto.

Nejprve tedy zkusíme, zda již jsou detaily dostupné.

    my $vyhovujici_liga = $vyhovujici[0]{"odkaz_liga"};
    my $vyhovujici_idzapasu = $vyhovujici[0]{"odkaz_idzapasu"};
    my $probihajici_minuta;

Pokud ne, budeme si na ně muset počkat. Periodicky budeme kontrolovat, zda již jsou dostupné.

    while(!$vyhovujici_idzapasu){
        @vyhovujici = $live->ziskej_zapasy_dane_ligy();
        @vyhovujici = $live->najdi_zapas_podle_kriterii(\@vyhovujici, \@vsechna_kriteria);

        $probihajici_minuta = $vyhovujici[0]{"minuta"}, "\n";
        last if($vyhovujici[0]{"hraje_se"} == Livescore::UKONCEN);
        if($vyhovujici[0]{"odkaz_idzapasu"}){
            $vyhovujici_idzapasu = $vyhovujici[0]{"odkaz_idzapasu"};
            $vyhovujici_liga = $vyhovujici[0]{"liga"};
        }

        if($vyhovujici[0]{"hraje_se"} == Livescore::PROBIHA){
            print "Probiha $probihajici_minuta'          \r";
        }elsif($vyhovujici[0]{"hraje_se"} == Livescore::PRED_VYKOPEM){
            print "Zapas zatim nezacal\r";
        }
        sleep $refresh;
    }

K tomu, aby se nám neuchovávala data ve výstupním bufferu zatímco je v činnosti funkce sleep je třeba připsat na začátek skriptu tyto dva řádky. Vyprazdňování bufferu musí být automatické.

use IO::Handle;
STDOUT->autoflush(1);

Pokud skončil předchozí cyklus, znamená to, že buď zápas skončil nebo probíhá a jsou dostupné události. V obou případech vytiskneme dostupné události. Jestliže zápas probíhá, budeme navíc tisknout přibyvší události dokud zápas také neskončí.

    do {
        my @udalosti = $live->prenos($vyhovujici_liga, $vyhovujici_idzapasu);
        $probihajici_minuta = shift @udalosti;
        $hraje_se = shift @udalosti;

        #vytiskneme nové události

        print "Probiha $probihajici_minuta'\r";
        sleep $refresh if $hraje_se == Livescore::PROBIHA;
    }while($hraje_se == Livescore::PROBIHA);

Nyní projdeme všechny události a ty, které jsou nové zobrazíme. ID starých událostí budeme kopírovat do pole @zobrazene_udalosti, abychom měli přehled o tom, co již bylo zobrazeno.

        for (@{$udalosti[0]}){
            next if in_array($_->{"id_udalosti"}, \@zobrazene_udalosti);

            #zobrazíme událost a zapíšeme do @zobrazene_udalosti

        }

Nyní zbývají poslední dva kroky. Zvolíme vhodnou formu zobrazení a opět pomocí funkce colored vytiskneme. Máme 3 druhy události - gól, žlutá karta a červená karta. Na základě prvku udalost můžeme u všech událostí rozhodnout, o který případ jde. Poté aktualizujeme pole @zobrazene_udalosti.

            if ($_->{"udalost"} eq "yellow"){
                print colored(sprintf("%2s'     %-20s (%s)\a\n", $_->{"minuta"},
                    $_->{"hrac"}, $_->{"tym"}), "bold yellow");
            }elsif ($_->{"udalost"} eq "red" or $5 eq "yellow-red"){
                print colored(sprintf("%2s'     %-20s (%s)\a\n", $_->{"minuta"},
                    $_->{"hrac"}, $_->{"tym"}), "bold red");
            }elsif ($_->{"udalost"} eq "goal"){
                print colored(sprintf("%2s' ", $_->{"minuta"}), "bold white");
                print colored(sprintf("%d:%d ", $_->{"skore1"}, $_->{"skore2"}),
                    "bold yellow");
                print colored(sprintf("%-20s (%s)\a\n", $_->{"hrac"}, $_->{"tym"}),
                    "bold white");
            }
            push @zobrazene_udalosti, $_->{"id_udalosti"};
        }

Za cyklus do-while se program dostane pouze v jediném případě - pokud skončil zápas. Tuto informaci tedy vytiskneme a na závěr zopakujeme aktualizovaný výsledek.

    print "Zapas skoncil\n";
    $live->ziskej_zapasy_dane_ligy;
    tiskni_vyhovujici($live->najdi_zapas_podle_kriterii(\@vyhovujici, \@vsechna_kriteria));
    exit;

Závěr

Nyní jsme hotovi. Všechny požadavky ze zadání projektu jsme úspěšně dokončili. Kompletní program si můžete stáhnout (Livescore.pm, live) a vyzkoušet.

live -o -l italy torino live -o li + interaktivní zadání live -o feyenoord

Výsledek zápasu *** Výsledek interaktivně vybraného zápasu *** Aktualizovaný probíhající online přenos

Samozřejmě by nyní tento program mohl být rozšířen o nové funkce. Například souběžné online přenosy více zápasů najednou, lepší členění pomocí přepínače -l a s tím související vylepšení cachování nebo přepis do Curses, Qt či jiného pokročilejšího uživatelského rozhraní.

Nicméně náš původní cíl je nyní splněn a proto tato šestidílná série, jejíž cílem bylo předvést některé techniky probrané v seriálu i z trochu jiného pohledu, dneškem končí.

Verze pro tisk

pridej.cz

 

DISKUZE

Nejsou žádné diskuzní příspěvky u dané položky.



Příspívat do diskuze mohou pouze registrovaní uživatelé.
> Vyhledávání software
> Vyhledávání článků

12.8.2018 16:58 /František Kučera
Srpnový pražský sraz spolku OpenAlt se koná ve čtvrtek – 16. 8. 2018 od 19:00 v Kavárně Ideál (Sázavská 30, Praha), kde máme rezervovaný salonek. Tentokrát jsou tématem srazu databáze prezentaci svého projektu si pro nás připravil Standa Dzik. Dále bude prostor, abychom probrali nápady na využití IoT a sítě The Things Network, případně další témata.
Přidat komentář

16.7.2018 1:05 /František Kučera
Červencový pražský sraz spolku OpenAlt se koná již tento čtvrtek – 19. 7. 2018 od 18:00 v Kavárně Ideál (Sázavská 30, Praha), kde máme rezervovaný salonek. Tentokrát bude přednáška na téma: automatizační nástroj Ansible, kterou si připravil Martin Vicián.
Přidat komentář

18.6.2018 0:43 /František Kučera
Červnový pražský sraz spolku OpenAlt se koná již tento čtvrtek – 21. 6. 2018 od 18:00 v Kavárně Ideál (Sázavská 30, Praha), kde máme rezervovaný salonek. Tentokrát na téma: F-Droid, aneb svobodný software do vašeho mobilu. Kromě toho budou k vidění i vývojové desky HiFive1 se svobodným/otevřeným čipem RISC-V.
Přidat komentář

23.5.2018 20:55 /Ondřej Čečák
Od pátku 25.5. proběhne na Fakultě informačních technologií ČVUT v Praze openSUSE Conference. Můžete se těšit na spostu zajímavých přednášek, workshopů a také na Release Party nového openSUSE leap 15.0. V na stejném místě proběhne v sobotu 26.5. i seminář o bezpečnosti CryptoFest.
Přidat komentář

20.5.2018 17:45 /Redakce Linuxsoft.cz
Ve čtvrtek 31. května 2018 připravuje webový magazín BusinessIT ve spolupráci s Best Online Média s.r.o. pátý ročník odborné konference Firemní informační systémy 2018. Akce proběhne v kongresovém centru Vavruška (palác Charitas), Karlovo náměstí 5, Praha 2 (u metra Karlovo náměstí) od 9:00 hod. dopoledne do cca 15 hod. odpoledne. Konference je zaměřena na efektivní využití firemních informačních systémů a na to, jak plně využít jejich potenciál. Podrobnější informace na webových stránkách konfrence.
Přidat komentář

14.5.2018 7:28 /František Kučera
Květnový pražský sraz spolku OpenAlt se koná již tento čtvrtek – 17. 5. 2018 od 18:00 v Kavárně Ideál (Sázavská 30, Praha), kde máme rezervovaný salonek. Tentokrát na téma: Audio – zvuk v GNU/Linuxu.
Přidat komentář

7.5.2018 16:20 /František Kučera
Na stránkách spolku OpenAlt vyšla fotoreportáž Pražské srazy 2017 dokumentující srazy za uplynulý rok. Květnový pražský sraz na téma audio se bude konat 17. 5. 2018 (místo a čas ještě upřesníme).
Přidat komentář

17.4.2018 0:46 /František Kučera
Dubnový pražský sraz spolku OpenAlt se koná již tento čtvrtek – 19. 4. 2018 od 18:00 v Kavárně Ideál (Sázavská 30, Praha), kde máme rezervovaný salonek. Tématem tohoto srazu bude OpenStreetMap (OSM) aneb svobodné mapy.
Přidat komentář

   Více ...   Přidat zprávičku

> Poslední diskuze

20.2.2018 18:48 / Ivan Majer
portal

20.2.2018 15:57 / Jan Havel
Jak využíváte služby cloudu v podnikání?

16.1.2018 1:08 / Ivan Pittner
verejna ip od o2 ubuntu

15.1.2018 17:26 / Mira Harvalik
Re: Jak udělat HTML/Javascript swiping gallery do mobilu?

30.12.2017 20:16 / Michal Knoll
odmocnina

Více ...

ISSN 1801-3805 | Provozovatel: Pavel Kysilka, IČ: 72868490 (2003-2018) | mail at linuxsoft dot cz | Design: www.megadesign.cz | Textová verze