Kde dělám chybu? – PHP – Fórum – Programujte.com
 x   TIP: Přetáhni ikonu na hlavní panel pro připnutí webu

Kde dělám chybu? – PHP – Fórum – Programujte.comKde dělám chybu? – PHP – Fórum – Programujte.com

 

martinb19840
Newbie
11. 7. 2014   #1
-
0
-

   

<?php
$dotaz1 = "SELECT * FROM nabidka WHERE nabidka_kategorie = 'Jídlo'";
$vysledek1 = mysql_query($dotaz1) or die(mysql_error() );

while($radek1 = mysql_fetch_array($vysledek1)) {
   	extract($radek1);
	echo "<h1> $nabidka_skupina </h1>";

	$dotaz2 = "SELECT * FROM nabidka WHERE nabidka_skupina = '$nabidka_skupina'";
        $vysledek2 = mysql_query($dotaz2) or die(mysql_error() );

	 while($radek2 = mysql_fetch_array($vysledek2)) {
            extract($radek2);
	    echo "1. $nabidka_nazev, nabídka_cena <br />";

     }	
} 
?>

Tak už jsem celkem bezradný. Protože skript obsahuje mnoho formátovacích prvků, uvedu zde pro jednoduchost pouze "kostru" bez jakéhokoli formátování. Mám databázi a v ní tabulku "nabídka". V této tabulce se nachází jídelní lístky. Kromě názvu jídla, ceny či množství apod. jsou zde sloupce kategorie (označuje selekci mezi "jídlo", "pití") a sloupec "skupina", který označuje podskupinu např. kategorie jídlo a podskupina předkrmy, polévky apod. Cílem je vypsat tabulku tak, aby se zobrazila následovně:

Předkrmy

1. jeden předkrm 100 Kč

2. předkrm 200 Kč

Polévky

1. polévka slepičí 25 Kč

2. ....

atd. Jak na to? Logicky mi přišlo správné napsat skript, který jsem Vám zde uveřejnil. Skript funguje prakticky správně, ale nadpis i všechna jídla pod ním se vypíše 2x tzn.

Polévky

1. p1

2. p2

Polévky

1. p1

2.p2

Proč?? Kde dělám chybu?

Nahlásit jako SPAM
IP: 89.176.190.–
martinb19840
Newbie
11. 7. 2014   #2
-
0
-

   

<?php
$a = "";
$dotaz1 = "SELECT * FROM nabidka WHERE nabidka_kategorie = 'Jídlo'";
$vysledek1 = mysql_query($dotaz1) or die(mysql_error() );

while($radek1 = mysql_fetch_array($vysledek1)) {
   	extract($radek1);
	if($a!=$nabidka_skupina)  {
	echo "<h1> $nabidka_skupina </h1>";

	$dotaz2 = "SELECT * FROM nabidka WHERE nabidka_skupina = '$nabidka_skupina'";
        $vysledek2 = mysql_query($dotaz2) or die(mysql_error() );

	 while($radek2 = mysql_fetch_array($vysledek2)) {
            extract($radek2);
	    echo "1. $nabidka_nazev, nabídka_cena <br />";

     }	
   }
} 
?>

Jako částečné řešení mě napadlo dát ověřovací podmínku - viz. vložený zdroják, jenže to řeší problém jen částečně. Celý skript je součástí redakčního systému a vše funguje jen do doby, než se někdo rozhodne do již hotového jídeláku vepsat do jedné ze skupin další položku... V tu ránu se celá skupina opět vypíše dvakrát..

Nahlásit jako SPAM
IP: 89.176.190.–
martinb19840
Newbie
11. 7. 2014   #3
-
0
-

Chyba je toto: Pokud je v každé skupině jen jeden záznam, funguje vše jak má. Pokud se záznamy přidávají postupně tzn. nejprve jedna skupina, v ní x záznamů a pak další a další, vše funguje, jak má. Problém je, že jakmile dodatečně přidám záznam do nějaké skupiny a tento záznam se zařadí nakonec databáze (má nejvyšší ID), vše se ve výpisu rozdvojí. Když pak ručně v databázi zařadím záznam za záznamy v dané skupině, vše je opět v pořádku.

Nahlásit jako SPAM
IP: 89.176.190.–
martinb19840
Newbie
11. 7. 2014   #4
-
0
-

Analýza chyby:

1. skript prochází hodnoty. Narazí na hodnotu "nabídka_skupina", tuto vypíše a následně vypíše všechny záznamy, které tuto hodnotu mají. To je ok.

2.cyklus běží podruhé a narazí na jinou skupinu, tuto opět vypíše a opět se vrací na začátek. Protože nový záznam se vepsal nakonec tabulky, narazí po nějakém čase opět na tu první skupinu, do které byl záznam vložený a proto ji znova vypíše. Vypíše ji tolikrát, kolikrát se vloží nový záznam na konec tabulky s nejvyšším ID.

Takže chyba je jasná. Teď jde o to, jak to ošetřit. Nejlepší by bylo zařazovat záznamy dané skupiny vždy ne na konec tabulky, ale na konec záznamů v dané skupině. Jde to nějak?

Nahlásit jako SPAM
IP: 89.176.190.–
Kit+15
Guru
11. 7. 2014   #5
-
0
-

#4 martinb1984
Volat SQL dotaz uvnitř cyklu řízeného jiným SQL dotazem je jízdenkou do pekel. Dej to do jednoho SQL dotazu a budeš mít klid.

Nahlásit jako SPAM
IP: 46.174.34.–
Komentáře označují místa, kde programátor udělal chybu nebo něco nedodělal.
martinb19840
Newbie
11. 7. 2014   #6
-
0
-

#5 Kit
1. jj, vím, ale jak docílit takového výpisu v jednom SQL dotazu? Napiš konkrétně, mně nic nenapadá..

2. daný problém to neřeší..

Nahlásit jako SPAM
IP: 89.176.190.–
Kit+15
Guru
11. 7. 2014   #7
-
0
-

#6 martinb1984

  • Především se zbav EAV v návrhu databáze. Pracuje se s tím hodně blbě a je to líné. Rozděl to na dvě tabulky.
  • Funkce extract() má dělat co? Tohle použití je hodně nebezpečné a zřejmě způsobuje tvůj problém.
  • Jako obvykle tam máš SQL injekci. Zkus zařadit kategorii "Gordon's menu" a skript se ti sesype.
  • Zaveď si do tabulek syntetické primární klíče, ať se z toho nezblázníš.

Nahlásit jako SPAM
IP: 46.174.34.–
Komentáře označují místa, kde programátor udělal chybu nebo něco nedodělal.
martinb19840
Newbie
11. 7. 2014   #8
-
-1
-
Mimo téma
Kit -

#7 Kit
Dík, toto, co píšeš, je pravda, na straně druhé je také pravda, že mám pod rukama redakční systém, který jsem psal již dříve, má nějaké "neduhy" např. to, co zmiňuješ a vše se změní v následující verzi. Takže rady určitě dobré, ale ve chvíli, kdy máte pod rukama redakčák se stovkami klientů a pěkně naducanou databází, tak je prostě nesmysl mi radit toto. To, co potřebuji je rychle vyřešit problém, který jsem napsal a fce extract() s tím nemá nic společného, injekce také ne (je samozřejmě ošetřeno javascriptem u vkládání v rámci textového pole). Je škoda, že tu nezazněl rada, která by byla rychlá a účinná, nakonec jsem si ji vymyslel sám. Celé řešení problému se rovná třem řádkům kódu - a to při vložení nového záznamu si prostě načtu poslední ID dané skupiny, následně SQL dotazem zvětším o 1 každé následující ID a d vzniklé mezery vložím nový zázam. Jednduché, rychlé a je po problému :)

Nahlásit jako SPAM
IP: 89.176.190.–
Kit+15
Guru
11. 7. 2014   #9
-
0
-

#8 martinb1984
Je fajn, že sis to vyřešil. Hlavně aby si někdo z tohoto bastlení nevzal příklad.

Nahlásit jako SPAM
IP: 46.174.34.–
Komentáře označují místa, kde programátor udělal chybu nebo něco nedodělal.
Zjistit počet nových příspěvků

Přidej příspěvek

Toto téma je starší jak čtvrt roku – přidej svůj příspěvek jen tehdy, máš-li k tématu opravdu co říct!

Ano, opravdu chci reagovat → zobrazí formulář pro přidání příspěvku

×Vložení zdrojáku

×Vložení obrázku

Vložit URL obrázku Vybrat obrázek na disku
Vlož URL adresu obrázku:
Klikni a vyber obrázek z počítače:

×Vložení videa

Aktuálně jsou podporována videa ze serverů YouTube, Vimeo a Dailymotion.
×
 
Podporujeme Gravatara.
Zadej URL adresu Avatara (40 x 40 px) nebo emailovou adresu pro použití Gravatara.
Email nikam neukládáme, po získání Gravatara je zahozen.
-
Pravidla pro psaní příspěvků, používej diakritiku. ENTER pro nový odstavec, SHIFT + ENTER pro nový řádek.
Sledovat nové příspěvky (pouze pro přihlášené)
Sleduj vlákno a v případě přidání nového příspěvku o tom budeš vědět mezi prvními.
Reaguješ na příspěvek:

Uživatelé prohlížející si toto vlákno

Uživatelé on-line: 0 registrovaných, 9 hostů

Podobná vlákna

Kde mám chybu? — založil Anonymní uživatel

Kde mám chybu? — založil takinoo

Kde mám chybu? — založil tomáš polz

 

Hostujeme u Českého hostingu       ISSN 1801-1586       ⇡ Nahoru Webtea.cz logo © 20032024 Programujte.com
Zasadilo a pěstuje Webtea.cz, šéfredaktor Lukáš Churý