| MySql ORDER BY in paginacija - optimizacija | ||
|---|---|---|
|
ernest1a
28. mar 2010 16:36:05
Pridružen od: 27. feb 2007 335 objav 172 8 1 |
#1
Imam situacijo, ko imam v bazi več kot 200.000 zadetkov, ki ustrezajo kriterijem. Torej SELECT id FROM karnekej WHERE karnekej2>100 AND ... bi vrnilo 200.000 zadetkov. Problem nastane ker se ti queriji izvajajo zelo pogosto. V headerju bi rad prikazoval na random 10 rezultatov na vsak prikaz strani. LIMIT 10 sicer izjemno skrajša čas, toda ko se temu doda ORDER BY rand() vzame skoraj isto časa kot če bi zahteval vse. SELECT MAX(id)... je enako potraten pa niti ne pomaga kaj dosti. Če pa dam samo LIMIT 10, se mi bodo prikazovali vedno isti prvi rezultati, tisti zadnji pa nikoli. Ima kdo kako idejo kako rešit zadevo? Drugi primer pa je isti, le da moram k temu pa moram potem dodati še paginacijo kar še dodatno zakomplicira zadevo. Tudi tu dobrodošla kak ideja, bom pa vesel že če zna kdo odgovorit na prvi primer. Hvala! |
|
|
bostjan
28. mar 2010 16:48:14
Pridružen od: 31. jul 2008 643 objav 689 30 9 |
#2
Moje mnenje je, da načeloma random ni treba narediti ravno RANDOM. TTL daš odvisno od podatkov. Sedaj če je to neka internet stran pomoje preden uporabnik dojame, da random deluje na 100 zapisih in ne na 200k zapisih pri tem ko prikazuješ 10 podatkov je zlo majhna. Če pa že opazi se mu pa zdi, da je imel pač srečo in je random tako zbral :D |
|
|
schtr4jh
28. mar 2010 16:57:43
Pridružen od: 24. nov 2008 402 objav 322 33 4 |
#3
Random: Random paginacija mislim, da ni dobra rešitev za to. Ker bi v tvojem primeru za moj način "nekam" moral shranit 20.000 različnih arrayov, da se zapisi ne bi ponavljali. Najbolje bi bilo, da paginacijo narediš z order by id limit x,y. |
|
|
blackmamba
28. mar 2010 17:34:55
Pridružen od: 4. mar 2008 559 objav 392 25 11 |
#4
Mogoče tole pomaga: pa še članek, kjer sem to izluščil :) KLIK |
|
|
Kami
29. mar 2010 13:04:14
Pridružen od: 7. okt 2007 52 objav 20 1 5 |
#5
RAND() je že tako počasen, LIMIT nekovelikoštevilo, 1 pa je na večjih datasetih v večini primerov tudi zelo počasen. Če se ti SELECT MAX(id) .... LIMIT 1 izvaja enako počasi, potem sem sam skoraj brez kakšnih drugih konkretnih predlogov. Sicer vseeno menim, da se ti ta stavek ne bi smel izvajati skoraj enako dolgo in bi ta rešitev morala delovati v redu (torej dobiš max id, nato programsko naključno generiraš toliko različnih idjev, kot jih pač potrebuješ, na koncu pa SELECT-aš vrstice s temi ID-ji iz baze). Ena izmed "ne ravno lepih" rešitev, ki se jo še trenutno spomnim pa je ta, da bi v tabeli dodal še eno polje, kjer bi vedno ob vnosu vpisal naključno vrednost, potem bi namesto RAND() sortiral po tem stolpcu. Seveda bi ta stolpec moral biti indeksiran, rabil bi pa še neko skripto, ki bi na primer vsako noč šla čez vse vrstice v tej tabeli in bi posodobila naključne vrednosti v tem novem stolpcu. |
|
|
blackmamba
29. mar 2010 13:51:07
Pridružen od: 4. mar 2008 559 objav 392 25 11 |
#6
Testirano na 140.000 zapisih: ~ 1.8 sekunde Spodnji primer pa 0.28 sekunde.
|
|
|
ernest1a
30. mar 2010 13:24:47
Pridružen od: 27. feb 2007 335 objav 172 8 1 |
#7
Hvala za vse ideje! Sem se odločil da je res nesmiselno prikazovati random vseh x00.000 zadetkov, tako da bom uporabil LIMIT 5000 in while loop. Celoten proces brez while loop vzame 0.078 s, z while pa 0.094s (testirano z ab.exe). Sem mislil da sta while in mysqlfetchassoc bolj potratna. |
|