Generovaní nejen fotbalové tabulky

Publikováno v sekci PHP v Neděli 13.1.2008 - 19:48

V tomto článku si ukážeme jak generovat fotbalovou tabulku. S menšimi úpravami můžeme samozřejme generovat nejenom fotbalovou tabulku ale i tabulku z dalších sportovních odvětví.

if(isset($_POST['do'])) 
{

    if($_POST['b1']==$_POST['b2']) { //remiza
    mysql_query("UPDATE tabulka SET r=r+1, gf = gf+$_POST[b1], ga = ga+$_POST[b2], pz=pz+1, body=body+1 WHERE id = '$_POST[1]'");   //prvni

    mysql_query("UPDATE tabulka SET r=r+1, gf = gf+$_POST[b1], ga = ga+$_POST[b2], pz=pz+1, body=body+1 WHERE id = '$_POST[2]'"); //druhy
        
    } elseif($_POST['b1']<$_POST['b2']) { //vyhral b2
    
  mysql_query("UPDATE tabulka SET p=p+1, gf = gf+$_POST[b1], ga = ga+$_POST[b2],pz=pz+1 WHERE id = '$_POST[1]'");   //prvni

    mysql_query("UPDATE tabulka SET v=v+1, gf = gf+$_POST[b2], ga = ga+$_POST[b1], pz=pz+1, body=body+3 WHERE id = '$_POST[2]'"); //druhy   
    
    } elseif($_POST['b1']>$_POST['b2']) { //vyhral b1
    
    mysql_query("UPDATE tabulka SET v=v+1, gf = gf+$_POST[b1], ga = ga+$_POST[b2], pz=pz+1, body=body+3 WHERE id = $_POST[1]"); //prvni

    mysql_query("UPDATE tabulka SET p=p+1, gf = gf+$_POST[b2], ga = ga+$_POST[b1], pz=pz+1 WHERE id = $_POST[2]"); //druhy      
}
}

Výhodou: je velmi rychlý výběr z DB

Nevýhodou: může být oprava údajů. Budeme si muset vytvořit další formulář a zpracující skript, který by nám zpětně odmazal / upravil data. Je to spousty zbytečného skriptovaní navíc.

Způsob číslo 2

Tento způsob spočívá v tom, že si vytáhnem z databáze všechny odehrané zápasy, poukládáme si data do pole ( rozhodovacími mechanismy zjistíme kdo měl kolik výher, remíz, proher atd. ) a výsledné pole zapíšeme do databáze za jednotlivé týmy.

function reCount()
  {
     $sql = "SELECT d_tym, h_tym, d_goly, h_goly, kontumace, trest1, trest2
             FROM vysledky 
             WHERE schvaleno = 2
             AND id_souteze = $this->soutezID";


             
     $msql = mq($sql);
     if (mnr($msql))
     {
        // inicializace
        $this->init(&$data);
        
        while ($r = mfo($msql))
        {
          // nastaveni promennych
          $domaci = $r->d_tym;
          $hoste  = $r->h_tym;
          $g1     = $r->d_goly;
          $g2     = $r->h_goly;
          $kontumace = $r->kontumace;
          $trest1 = $r->trest1;
          $trest2 = $r->trest2;
          
          // vypocet
          
          // domaci vyhrali
          if ($g1 > $g2 && $kontumace != 3)
          {
            // nastavime domaci
            $data[$domaci]["pz"]++;
            $data[$domaci]["v"]++;
            //$data[$domaci]["r"]++;
            //$data[$domaci]["p"]++;
            $data[$domaci]["gf"] += $g1;
            $data[$domaci]["ga"] += $g2;
            $data[$domaci]["pts"] += 3;
            $data[$domaci]["trest"] += $trest1;
            
            // nastavime hosty
            $data[$hoste]["pz"]++;
            //$data[$hoste]["v"]++;
            //$data[$hoste]["r"]++;
            $data[$hoste]["p"]++;
            $data[$hoste]["gf"] += $g2;
            $data[$hoste]["ga"] += $g1;
            //$data[$hoste]["pts"] += 3;
            $data[$hoste]["trest"] += $trest2;
            
          }
         // vyhrali hoste 
         elseif ($g1 < $g2 && $kontumace != 3)
         {
            // nastavime domaci
            $data[$domaci]["pz"]++;
            //$data[$domaci]["v"]++;
            //$data[$domaci]["r"]++;
            $data[$domaci]["p"]++;
            $data[$domaci]["gf"] += $g1;
            $data[$domaci]["ga"] += $g2;
            //$data[$domaci]["pts"] += 3;
            $data[$domaci]["trest"] += $trest1;
            
            // nastavime hosty
            $data[$hoste]["pz"]++;
            $data[$hoste]["v"]++;
            //$data[$hoste]["r"]++;
            //$data[$hoste]["p"]++;
            $data[$hoste]["gf"] += $g2;
            $data[$hoste]["ga"] += $g1;
            $data[$hoste]["pts"] += 3; 
            $data[$hoste]["trest"] += $trest2;        
         } 
        // remiza 
        elseif ($g1 == $g2 &&  $kontumace != 3)
        {
            // nastavime domaci
            $data[$domaci]["pz"]++;
            //$data[$domaci]["v"]++;
            $data[$domaci]["r"]++;
            //$data[$domaci]["p"]++;
            $data[$domaci]["gf"] += $g1;
            $data[$domaci]["ga"] += $g2;
            $data[$domaci]["pts"] += 1;
            $data[$domaci]["trest"] += $trest1;
            
            // nastavime hosty
            $data[$hoste]["pz"]++;
            //$data[$hoste]["v"]++;
            $data[$hoste]["r"]++;
            //$data[$hoste]["p"]++;
            $data[$hoste]["gf"] += $g2;
            $data[$hoste]["ga"] += $g1;
            $data[$hoste]["pts"] += 1; 
            $data[$hoste]["trest"] += $trest2;                
        }
        // kontumace pro oba 
        elseif ($g1 == $g2 &&  $kontumace == 3)
        {
            // nastavime domaci
            $data[$domaci]["pz"]++;
            //$data[$domaci]["v"]++;
            //$data[$domaci]["r"]++;
            $data[$domaci]["p"]++;
            $data[$domaci]["gf"] += 0;
            $data[$domaci]["ga"] += 3;
            //$data[$domaci]["pts"] += 1;
            $data[$domaci]["trest"] += $trest1;
            
            // nastavime hosty
            $data[$hoste]["pz"]++;
            //$data[$hoste]["v"]++;
            //$data[$hoste]["r"]++;
            $data[$hoste]["p"]++;
            $data[$hoste]["gf"] += 0;
            $data[$hoste]["ga"] += 3;
            //$data[$hoste]["pts"] += 1;
            $data[$hoste]["trest"] += $trest2;               
        }        
          
      } // while end
    } // numrows > 0 ?
  

  
  
  } 

 function insertData($data)
  {
     if (is_array($data))
     {
       foreach ($data as $tymID => $pole)
       {
         $ins  = "INSERT INTO tabulka_poradi SET ";
         $ins .= " id_tymu = $tymID,
                   kolo = $this->round,
                   id_souteze = $this->soutezID,
                   pz = '{$data[$tymID]["pz"]}',
                   v = '{$data[$tymID]["v"]}',
                   r = '{$data[$tymID]["r"]}',
                   p = '{$data[$tymID]["p"]}',
                   gf = '{$data[$tymID]["gf"]}',
                   ga = '{$data[$tymID]["ga"]}',
                   pts = '{$data[$tymID]["pts"]}',
                   trest = '{$data[$tymID]["trest"]}'
                 ";
         
         //echo $ins . "<br />";
         $ins = mq($ins);    
         //echo mysql_error();     
       }
     }
  }

Výhoda: pořád se jedná o velmi rychlý počin a pokud se stane , že bychom nějaký zápas zrušili nebo mu potřebovali upravit výsledek, není nic jednoduššího než tabulku z DB vymazat a znovu ji přegenerovat.

Nevýhoda: pokud se bude jednat o větší množství zápasů ( tisíce položek), netuším co to udělá s pamětí, může dojít k alokaci paměti a shození stránky. Ja jsem generovával vždy několik desítek či stovek zápasů a neměl jsem problém. Další nevýhodu vidím v tom, že pokud si budete chtít tabulku zobrazovat po jednotlivých kolech, budete Vám databáze nepřijemně narůstat.

Způsob číslo 3

Všechno za Vás vyreší databáze

SELECT
ts.nazev, ts.seo_nazev,
tym,
SUM(W) + SUM(R) + SUM(P) as zapasy,
SUM(W) as vyhry,
SUM(R) as remizy,
SUM(P) as prohry,
SUM(G1) as goly_vstrelene,
SUM(G2) as goly_obdrzene,
SUM(G1) - SUM(G2) as rozdil,
SUM(W) * 3  + SUM(R) * 1 as body

FROM

(


SELECT id_domaci AS tym, SUM(
IF (
g1 > g2, 1, 0
) ) AS W, SUM(
IF (
g1 = g2, 1, 0
) ) AS R, SUM(
IF (
g1 < g2, 1, 0
) ) AS P, SUM( g1 ) AS G1, SUM( g2 ) AS G2
FROM vysledky
WHERE schvaleno = '1'
AND kolo <= $kolo
AND id_souteze = $soutez
GROUP BY tym

UNION ALL

SELECT id_hoste AS tym, SUM(
IF (
g1 < g2, 1, 0
) ) AS W, SUM(
IF (
g1 = g2, 1, 0
) ) AS R, SUM(
IF (
g1 > g2, 1, 0
) ) AS P, SUM( g2 ) AS G1, SUM( g1 ) AS G2
FROM vysledky
WHERE schvaleno = '1'
AND kolo <= $kolo
AND id_souteze = $soutez
GROUP BY tym

) TMP


JOIN  seznam_tymu as ts
ON ts.ID = TMP.tym
GROUP BY tym
ORDER BY body DESC, rozdil  DESC, goly_vstrelene DESC, zapasy DESC, nazev ASC

Výhoda: vše reší tento náročnější SQL dotaz. Neni složitý, jen trošku delší na napsání. Tímto vykreslíme tabulku do konkretního kola a není problém si zobrazit údaje z jiného kola. Pokud potřebujeme opravit zápas, opravujeme ho pouze v konkretní tabulce zápasu a o výsledné zobrazení se nestaráme. Takže časová úspora je myslím zřejmá.

Nevýhoda: bude v tom, že se bude databázový server více namáhat, než kdyby pouze tahal připravená data. On je musí počítat, setřídit a předložit. Pokud tabulku dobře osázíte indexy a těch zápasů tam nebudou tisíce ( žiju v domnění, že zobrazujeme tabulku z konkretní sézony kde proběhlo pár desítek či stovek zápasů), tak se nemusíme bát. Mám ješte složitejší dotaz, pospojováno více tabulek dohromady a výsledky jsou velmi slušné, rychlost je vždy kolem 0,005 s.

Sami si zvolte způsob, který se Vám nejvíce líbí. Tento článek není návodem, který pomocí copy & paste uvedete v pochod. Pokud znáte jiný způsob generování, vyjádřete se do komentáře.

20 komentářů « Zpět


Komentáře

reagovat #1 Fery:
26.09.08 22:02
Zdravim, je ten 3. způsob funkční? Pokoušel jsem se ho s malými úpravy aplikovat a nějak se mi nedaří. Díky
reagovat #2 Fery:
26.09.08 22:12
Aha, jsem tupec, nic :)
reagovat #3 Roman janko:
28.09.08 20:21
[2] Fery Mel by byt funkcni, je to jeden z typu dotazu, ktere pouzivam na svych sportovnich webech. Urcite ale neslouzi k tomu, aby ho nekdo past do phpmyadminu a pak se divil ze nefunguje. Kazdy si ho musi "ohnout" sam do sveho systemu, je to spise takove zamysleni a ukazka. Ale melo by to fungovat :)
reagovat #4 Fery:
21.10.08 17:53
Jj, funguje, udělal jsem tam školáckou chybu,nevypsal si mysql_error() a divil se jak puk, proč mi to nejde. Jinak díky, hodně mi pomohl tvůj příklad :)
reagovat #5 kubyk:
07.01.09 23:22
ale romane, jaktoze tam nenapises dik cloveku, kterej ti musel vysvetlit zaklady celyho tohodle procesu co? :) Jaktoze furt na tebe nekde narazim, at vlezu do jakykoliv diskuze, zase narazim na tebe :)
reagovat #6 Roman Janko: (Administrátor) admin@rjwebdesign.net
08.01.09 00:06
[5] kubyk Jakej kubyk? :) ( Znam 3x )
reagovat #7 harry:
29.09.09 15:39
Měl bych dotaz, dá se u toho posledního příkladu nějak omezit, aby to vypsalo můj tým (takže např. tým s id 1) a k tomu 3 týmy nad ním a 3 týmy pod ním? Díky
reagovat #8 Roman Janko: (Administrátor) admin@rjwebdesign.net
30.09.09 10:19
[7] harry Samozrejme

Viz. eldragon.pesonline.cz/statistiky/detail-…

nebo www.pesonline.cz/statistika/tym-v-sezone…

Nejsnazsi reseni je v aplikacni vrstve (cili v PHP) , ulozit radky do pole kde je klicem id tymu , pote si zjistit jeho pozici a jednoduchymi podminkami zajistit aby se zobrazily tymy pod nim a nad nim, v pripade ze je posledni ci prvni tak pouze nad nim resp pod nim.
24.06.10 09:01
Zdravim, chtěl bych poprosit o pomoc, už mě nebaví ručně zapisovat do tabulek, byl by někdo ochoten mě spravit autonatickej zápis+odehrane zápasy, stále se mě to nedaří tak hledám pomoc, tady je ukazka tabulek NHL nhlsezonahraonline.717.cz/menu/uvod
reagovat #10 Smoula:
15.07.10 22:02
Ahoj, vedel by si pomoct zo zadavanim vysledkov na cele kolo nie po jednotlivych zapasoch?

Vyberies kolo -> zapises vysledky naraz -> INSERTnes table..
Ď.
reagovat #11 Roman Janko: (Administrátor) admin@rjwebdesign.net
15.07.10 23:28
[10] Smoula Ano, samozřejmě. Jednotlivé inputy ponesou název pole. Tj.

<input name="gol1" type="text"/>

A poté projdeš post POLE a uložíš

foreach ($_POST["gol1"] ...)
16.07.10 15:05
[11] Roman Janko

Ahoj, mne sa paci ta 2.varianta - vytiahnes z DB aktualne zapasy, zadas vysledky a potom POSTnes, len nejako mi ten script nejde rozbehat :(
reagovat #13 Roman Janko: (Administrátor) admin@rjwebdesign.net
17.07.10 18:14
[12] Smoula Je to takový nástin, jak by to mohlo fungovat, vyjal jsem to jako torzo ze svého fotbalového webu.

Pokud máš nějaké základy v PHP tak to dáš dokupy, pokud ne, tak se PHP nejdřív trošku nauč, stejně bys později nevěděl složitejší věci i kdybych Ti s tímto pomohl.

:-)
17.07.10 21:57
.. sak to ze si to len "vyjal"... neboj zaklady mam dobre len ma zaujala tvoja 2.varianta na mojej stranke mam tiez aktualizaciu vysledkov, len trosku zlozitejsiu...

Ale ok.. idem sa potrapit :)
reagovat #15 Roman Janko: (Administrátor) admin@rjwebdesign.net
18.07.10 13:58
[14] Smoula Když nebudeš vědět něco konkrétního, klidně se zeptej, ale neptej se na celý skript :)
čaute...prosim vas ja by som velmi potreboval poradit s tou tretou variaciou tabulky....tam ju musim aj prepisat nejako alebo co???? nechapem tomu bol by som velmi vdacni autorovi alebo aj hocikomu inemu co by mi to vysvetlil dakujem
[16] Juraj To je ukázka jak vyrobit tabulku pomocí 1 SQL dotazu za předpokladu, že máš MySQL tabulku takto navrženou.
04.07.11 20:25
čau nemohol by si mi spraviť tú tabulku ? pls to čo si tam napiasl som nepochopil ani jednu vec
04.07.11 20:26
čau nemohol by si mi spraviť tú tabulku ? pls to čo si tam napiasl som nepochopil ani jednu vec
[19] Erik Nevím jakou tabulku, a pokud se takto ptáš tak skutečně nemohl, protože nemáš páru o čem se zde mluví.

Přidat komentář

Nový vzkaz

* Tato pole jsou povinná, [smajlíci]

  • na jiné komentáře odkazujte pomocí odkazu reagovat
  • vaše IP adresa bude zaznamenána
  • používají se gravatary
  • můžeme si tykat
  • HTML tagy vypnuty. PHP kód se také neprovede. Pokud potřebuju přiložit ukázku vašeho kódu, použijete službu pastebin, nebo jej vložte mezi značky [code] [/code]
  • vulgární, rasistické či jinak nepřípustné komentáře budou smazány