Zjisteni levelu stranky v rekurzivni funkci pri vypisu vsech stranek – PHP – Fórum – Programujte.com
 x   TIP: Přetáhni ikonu na hlavní panel pro připnutí webu
Reklama
Reklama

Zjisteni levelu stranky v rekurzivni funkci pri vypisu vsech stranek – PHP – Fórum – Programujte.comZjisteni levelu stranky v rekurzivni funkci pri vypisu vsech stranek – PHP – Fórum – Programujte.com

 

Hledá se programátor! Plat 1 800 € + bonusy (firma Boxmol.com)
jara
~ Anonymní uživatel
24 příspěvků
25. 5. 2007   #1
-
0
-

Dobry den,

mam nasledujici tabulku

CREATE TABLE `stranky` (
`id` smallint(6) NOT NULL auto_increment,
`nazev` varchar(100) NOT NULL default '',
`parent_node` varchar(10) NOT NULL default '0',
PRIMARY KEY (`id`)
)

kde parent_node je rodic nadrazene stranky. Jedna se o klasicky katalog stranek
napr. s temito daty:

1 | Home | 0
2 | O firme | 1
3 | Kontakt | 1
4 | Historie | 2

touto rekurzivni funkci vypisuju vsechny stranky katalogu



function generate_pages ($parent) {


$sql = 'SELECT * FROM stranky
WHERE parent_node LIKE "'.$parent.'"
';


$q = MySQL_Query($sql) or Die("error generate menu pages");

$u = '';


while ($r = mysql_fetch_array($q)) {
$u .= '<tr><td>';
$u .= get_level_path($r['id']).' <a href="#">'.$r['nazev'].'</a>';
$u .= '</td></tr>';
$u .= generate_pages($r['id']);

}
return $u;

}


a touto zjistuji uroven stranky vudci nejvysimu rodici



function get_level_path ($id) {
global $lev;

if(!isset($lev)) $lev = 0;
$result = mysql_query('SELECT * FROM stranky
WHERE id="'.$id.'"'
)
or die("error path stranky 1");
$row = mysql_fetch_array($result);
$parent = $row['parent_node'];

if(!$parent == 0) {
get_level_path($parent);
$lev++;
}
return $lev ;


pokud volam get_level_path(4) - tak mi to vrati 2, coz je spravne

pokud uz to pouziji v druhe rekurzivni funkci, zjistuje to level dane stranky spatne

generate_pages (1) vrati

1 O firme
3 Historie
4 Kontakty

spravne by melo byt

2 O firme
3 Historie
2 Kontakty

dekuji za radu

Nahlásit jako SPAM
IP: ...–
Reklama
Reklama
Prog.0
Věrný člen
25. 5. 2007   #2
-
0
-

Chyba je niekde vo fn get_level_path. minimalne tam bude chyba s nulovanim $lev, ale nechce sa mi to studovat...
Skus si najprv nakreslit algoritmus, a az potom zacat pisat... Nejedna sa zas o tak zlozitu vec, kod musi byt jasny na prvy pohlad...

Hlavne sa skus vyhnut rekurzii a globanlym premennym. Ak chces kod, resp. algoritmus, tak ti ho tu urcite niekto hodi, mozem aj ja, ak budes chciet, ale skus sa este potrapit ;-)

Mala pripomienka: Nazov funkcie - get_level_by_path vo mne evokuje ze do vstupu sa bude zadavat stringova cesta:
get_level_by_path('/Home/O firme/Historie/') ... odporucam premenovat na get_level_by_id ;-)

Nahlásit jako SPAM
IP: ...–
Prog.
25. 5. 2007   #3
-
0
-

Udelat poradnou stromovou strukturu neni vubec zadna sranda. Je hafo moznosti, vetsina jich ale pouziva u vetsich stromu desitky nebo i vice MySQL dotazu, coz neni cesta. Ja osobne vim o dvou moznostech, ktere se tomu vyhybaji - jedna je pomoci MySQL uzivatelskych funkci (ty neovladam, takze jsem ji nejak hluboce nestudoval) a druha je pomoci predkompivaneho stromu. Ve zkratcce to vypada asi takhle: pozice vestrmu je udavana normalne pomoci ID rodice, cely strom je ale po kazde zmene treba rekompilovat. Pri rekompilaci se presne spocita pozice kazde polozky ve stromu a ta se pomoci dalsich dvou cisel ulozi k dane polozce do MySQL. Z techto dvou cisel se da potom spocitat napriklad prave uroven ve sromu , pocet deti nebo snad i pocet sourozencu (tim si ale nejsem jisty). A hlavni vyhoda je, ze cely strom se nacte pomoci jednoho jedineho MySQL dotazu.

Nahlásit jako SPAM
IP: ...–
Prosím, jestli potřebujete s něčím poradit,zeptejte se na fóru. Jakýkoliv bezdůvodný pokus mě kontaktovat skončí okamžitým přidáním do ignore listu![br][br] Současný počet osob, které to nepochopily: 7
Prog.0
Věrný člen
25. 5. 2007   #4
-
0
-

To CommanderZ: jednoducha parent-id structura ma tu nevyhodu, ze nuti uzivatela uchylit sa k rekurziam a k cyklickemu volaniu mnozstva selectov. Tomu, co si nacrtol sa nadava left-right struktura. Funguje rovnako ako klasicka parent-id ale navyse sa pri kazdom noode ukladaju dve dalsie hodnoty (left,right) ktore zavisia od celej struktury. s takouto struktorou sa velmi lahko a rychlo pracuje (vyberanie, hladanie a pod) ale pridavanie/odoberanie poloziek do stromu je o to narocnejsie. (stale je potrebne upravit left,right hodnoty).

Co sa tyka povodnej otazky, zistit level z parent-id struktury na zaklade id, to chce cyklus selectov az k nule. Pouzivat na to rekurziu este k tomu s globalnymi, uf, je akoby niekto hladal co najzlozitejsie riesenie :-)

BTW: ulozenie levelu to tabulky nie je ziadna chyba, ani pri parent-id, ani pri left-right.

To jara:

  function get_level_id($id)

{
$l = 1;
while($id=mySQL_result(mysql_query('
SELECT parent_node
FROM stranky
WHERE id='.$id
),0)) $l++;

return $l;
}
Ale neodporucam to pouzivat v pripade, ze zakazdym generujes celu strukturu. To radsej pouzi jeden select * from ... ( nacitaj celu tabulku) a phpckom potom vyberaj z resultu co potrebujes... (zlozitejsie ale rychlejsie)

Nahlásit jako SPAM
IP: ...–
Prog.
27. 5. 2007   #5
-
0
-

BTW: ulozenie levelu to tabulky nie je ziadna chyba, ani pri parent-id, ani pri left-right.



Jak jsem psal, pri tom left-rightu (jsem si nemohl vzpomenout, jak se tomu nadava) to jednoduse spocitas z tech dvou hodnot

Nahlásit jako SPAM
IP: ...–
Prosím, jestli potřebujete s něčím poradit,zeptejte se na fóru. Jakýkoliv bezdůvodný pokus mě kontaktovat skončí okamžitým přidáním do ignore listu![br][br] Současný počet osob, které to nepochopily: 7
Prog.0
Věrný člen
28. 5. 2007   #6
-
0
-

To s tym ulozenim levelu som myslel tak, ze ak do tabulky prihodim jeden stlpec - unsigned tinyint - (myslim ze 255 levelov kazdemu staci), vacsinou ho netreba ani indexovat, tak tym nijako rapidne nezvysim pamatove naroky. Rychlost vyberania sa zvysi, v porovnani so sql vyratavanim na zaklade left-right. Cas na vypocet levelu pri vkladani je len zlomkom z toho co sa spotrebuje na preratanie left-right hodnot. Pri jednoduchej parent-id by bol cas vkladania dlhsi, hlavne keby slo o vacsiu hlbku vnorenia. (cyklenie selectov).

Vyratavanie levelu z left-right hodnot funguje tak, ze jednym selectom vytiahnem vsetky riadky, nadradene noodu pre ktory to vyratavam (akoby som chcel zistit cestu, akou sa k nemu dostanem - jednoducho ich spocitam - a mam level)

zistenie celej cesty k noodu - tabulka nodov cez ktrore treba prejst az k pozadovanemu:

select node_name from struktura where node_left <= LEFT_HLADANEHO and node_right >= RIGHT_HLADANEHO order by node_left


zistenie levelu:
select count(*) as level from struktura where node_left <= LEFT_HLADANEHO and node_right >= RIGHT_HLADANEHO


Pouzivat toto, zakazdym ked treba level sa mi zda prilis pomale, v porovnai s tym jednym stlpcom... ide hlavne o to, ze ako casto je ten level vobec potrebny. (ja ho napriklad vobec nepouzivam :))


Hm, myslim ze by nebolo odveci napisat nejaky clanok o stromovych strukturach, teda, ak si niekto trufa - staci nieco jednoduche na prakticke pouzitie ;-)

Nahlásit jako SPAM
IP: ...–
Prog.
28. 5. 2007   #7
-
0
-

Ja bych to kdyztak splacat mohl, Curo ted ale nenabira ;)

Nahlásit jako SPAM
IP: ...–
Prosím, jestli potřebujete s něčím poradit,zeptejte se na fóru. Jakýkoliv bezdůvodný pokus mě kontaktovat skončí okamžitým přidáním do ignore listu![br][br] Současný počet osob, které to nepochopily: 7
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, 53 hostů

 

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