Autor Zpráva
wesna
Profil *
Ahoj,
mam csv souvbor s ceskou slovni zasobou.

Potrebuji vzdy overit, zda nejake slovo, ktere zadam ve slovniku je.

Jelikoz slov je hodne, rad bych se zeptala, jak by se dalo takove hledani udelat co nejefektivneji?

Nejlepe nejakou ukazku.

Cetla jsem, ze se na to pouziva metoda bucket sort ale zadny pekny priklad jsem nenasla.

Diky moc za radu.
Marek88
Profil
Je nutné slova ponechat v csv? Nejlepší by asi bylo je importovat do databáze. Je to jednoduché na realizaci a vyhledávání v DB je rychlé.
Krakatoa
Profil
Uložit slova, která je potřeba ověřit, do txt souboru např. zvlášť na řádek nebo oddělena nějakým oddělovačem.
Udělat skript (já bych to svedl např. v Autoitu a není to nic těžkého, podle nápovědy v autoitu bys to svedla též, pokud jsi technicky nadaná, ale stejně by to šlo i v php), který načte ten txt soubor a tvůj csv do paměti a to do pole nebo sqlite též uložené v paměti ... a pak to celé projel klidně i bez nějakého bucket sort algoritmu, fofr to bude i tak... a výstup si uděláš jaký chceš, např. slova, která nejsou v databázi nebo všechna slova se stavem nebo slova a vypsaný výskyt v csv...
wesna
Profil *
Diky, chci to realiovat urcite v PHP, vzdy se bude overovat jen jedno slovo. Spise mi neni jasne, jak provest to samostatne overovani.

Bud si ta slova nactu do pole a porovnavam jednotlive polozky pole se slovem a v pripade shody vypisi true, v pripade, ze se nic nenalezne, tak false.

Netusim jak na na samotne projeti pole..
Alphard
Profil
wesna:
in_array() by mohlo stačit.
Ale načíst do pole znamená načíst do paměti. Řadit to pak nemá moc smysl, bude to náročnější než 1x hledat ve všech položkách.
Jestli je těch slov fakt hodně, je databáze lepší.
Giga
Profil *
Keď už by sa to načítavalo do pamäti, tak by som to "presypal" do php súboru, ktorý by som includoval.
Ugo
Profil
po dlouhé době zajímavé téma které si musím zkusit, osobně si myslím že i v takovémhle objemu dat by mohlo být rychlejší pracovat s tím jako s řetězcem, čili strpos asi... jdu to zkusit všemožnejma variantama :-P

výsledek mojho měření, testováno na 4 místných kombinacích malých písmen - něco kolem 470 tis. 1-4 znakého textu. (mysql - tabulka s jedním sloupečkem, in_array struktura slovo;slovo;slovo, strpos struktura ;slovo;;slovo;;slovo; .. php array : <?php $conf['key']=true; -> isset($conf['key']) ) zkouseno pres apache benchmark - 50 pokusu

mysql : 140.623 ms ; 512 kb
in_array() : 326.860 ms ; 48.5 mb
strpos() : 20.937 ms ; 3.25 mb
php array : 1710.291 ms ; 126.25 mb
Keeehi
Profil
Pokud je ten soubor poměrně statický, použil bych seřazenou verzi. Pak se dá použít na vyhledávání třeba binární půlení. A pokud byste chtěl ušetřit paměťovou náročnost, tak by to snad mělo jít jen nad otevřeným souborem. Skákat v něm pomocí fseek a číst slova ne popořadě ale na přeskáčku. Až by se člověk dostal na interval třeba 100 znaků, prohledat to už lineárně. Mělo by to být rychlé i paměťově nenáročné.
wesna
Profil *
Tak jem zkusila toto, jednak to asi kazdou polozku ze slovniku uklada do samostatneho pole a za druhe to trva pekelne dlouho.


Nejake lepsi reseni? Soubor ma 800 000 slov.

<?php
$file = fopen('cs.dic', 'r');
while (($line = fgetcsv($file,1000, "\n")) !== FALSE) {
  //$line is an array of the csv elements
 // print_r($line);
}

if (in_array("abakus", $line)) {
    echo "slovo abakus je v poli";
}

fclose($file);
Alphard
Profil
wesna:
Psali jsme to už na začátku, naházejte to do databáze.

Alternativní možnosti, jako např. [#8], se jen snaží primitivně suplovat databázi.
Z testu [#7] jako nejlepší alternativa vypadá načíst to přes file_get_contents() a hledat přes strpos().
Kajman
Profil
Ugo:
mysql : 140.623 ms

A nad tím sloupečkem jste udělal index? Při 470 000 unikátních hodnotách mi to přijde nějak moc.
wesna
Profil *
Dobre, nahozeno do DB a jaky dotaz bych mela pouzit jako nejrychlejsi?

Staci mi, kdyz bude vracet pocet nalezenych slov.
Kajman_
Profil *
wesna:
Udělejte na sloupci (unikátní) index - v případě dlouhých slov můžete udělat index jen na prvních třeba 6 znacích.

Pro kontrolu jednoho slova, pak můžete udělat např.
select 1 existuje from tabulka where sloupec='hledaneslovo' limit 1
Keeehi
Profil
Můj postup nalezne odpověď v souboru se 100000 řádky za 3ms. Je pravda, že naprogramování( těch skoků, následné najití slova kolem té pozice, porovnání s hledaným, zjištění směru skoku a následný skok) je neskutečně hnusná práce, avšak pokud jde o rychlost (a paměťovou náročnost - neověřoval jsem, ale neměla by být vysoká) jde myslím o nejlepší řešení.
Tori
Profil
Keeehi:
za 3ms
To je přesná hodnota, nebo dopočítaná v odpovídajícím poměru k Ugovo měřením? (Třeba má o dost pomalejší stroj.)
edit: ten poměr jsem myslela tak, že byste provedl stejné testy jako on a pokud by vám vyšly třeba poloviční časy, tak byste místo 3ms dal 6ms.
Keeehi
Profil
Tori:
Vzhledem k neznámé Ugově konfiguraci to bude těžko dopočítané dle poměru. I kdybych tu konfiguraci znal, převodní "poměr" by se těžko získával. Takže je to absolutní číslo. Co vím je to, že můj stroj je cca 10x pomalejší než když to zkouším na webhostingu (Wedos - NoLimit).

Ale i kdyby měl starší stroj, tak výsledek je řádově srovnatelný akorát se strpos(). Co jsem zjistil jsem i paměť 335 kB, přičemž na začátku scriptu (bez otevření vstupu) zabírá script 325 kB, takže v průběhu scriptu vzrostou paměťové nároky jen o 10kB. Což je v porovnání s ostatními málo. V oblasti paměti by mohl být výsledek srovnatelný s databází. Ovšem nevím, zda se v Ugovém měření promítly i paměťové nároky databáze. Zda neměřil pouze paměť zabíranou scriptem.
Ugo
Profil
Omlouvám se za nejasnosti, databáze je defaultní xampp a na index jsem zapomněl, chtěl jsem napsat že při dobrém nastavení DB půjde ten čas asi razantně dolů.. ale nenapsal :-P. Stroj je pomalý neskutečně, tedy ne ta stroj jako xampp na widlích. Paměť jsem měřil jen scriptu, v db to není tak akutní jelikož strašák v podobě memory limitu mě tam nikdy nestrašil. Udělal jsem teď ještě ten index a výsledek je výborný ... 18ms. Takže pardón za opomenutí něčeho tak samozřejmého, ale aspoň je tu vidět i poměr jak moc se nechá lehce urychlit práce s db :)

Vaše odpověď

Mohlo by se hodit


Prosím používejte diakritiku a interpunkci.

Ochrana proti spamu. Napište prosím číslo dvě-sta čtyřicet-sedm: