abclinuxu.cz AbcLinuxu.cz itbiz.cz ITBiz.cz HDmag.cz HDmag.cz abcprace.cz AbcPráce.cz
AbcLinuxu hledá autory!
Inzerujte na AbcPráce.cz od 950 Kč
Rozšířené hledání
×
eParkomat, startup z ČR, postoupil mezi finalisty evropského akcelerátoru ChallengeUp!
Robot na pivo mu otevřel dveře k opravdovému byznysu
Internet věcí: Propojený svět? Už se to blíží...
dnes 06:00 | Zajímavý software

OMG! Ubuntu! představuje emulátor terminálu Hyper (GitHub) postavený na webových technologiích (HTML, CSS a JavaScript). V diskusi k článku je zmíněn podobný emulátor terminálu Black Screen. Hyper i Black Screen používají framework Electron, stejně jako editor Atom nebo vývojové prostředí Visual Studio Code.

Ladislav Hagara | Komentářů: 2
dnes 06:00 | Zajímavý článek

I letos vychází řada ajťáckých adventních kalendářů. QEMU Advent Calendar 2016 přináší každý den nový obraz disku pro QEMU. Programátoři se mohou potrápit při řešení úloh z kalendáře Advent of Code 2016. Kalendáře Perl Advent Calendar 2016 a Perl 6 Advent Calendar přinášejí každý den zajímavé informace o programovacím jazyce Perl. Stranou nezůstává ani programovací jazyk Go.

Ladislav Hagara | Komentářů: 2
3.12. 16:24 | Nová verze

Byla vydána Mageia 5.1. Jedná se o první opravné vydání verze 5, jež vyšla v červnu loňského roku (zprávička). Uživatelům verze 5 nepřináší opravné vydání nic nového, samozřejmě pokud pravidelně aktualizují. Vydání obsahuje všechny aktualizace za posledního téměř půldruhého roku. Mageia 5.1 obsahuje LibreOffice 4.4.7, Linux 4.4.32, KDE4 4.14.5 nebo GNOME 3.14.3.

Ladislav Hagara | Komentářů: 8
3.12. 13:42 | Pozvánky

V Praze probíhá konference Internet a Technologie 16.2, volné pokračování jarní konference sdružení CZ.NIC. Konferenci lze sledovat online na YouTube. K dispozici je také archiv předchozích konferencí.

Ladislav Hagara | Komentářů: 0
2.12. 22:44 | Komunita

Joinup informuje, že Mnichov používá open source groupware Kolab. V srpnu byl dokončen dvouletý přechod na toto řešení. V provozu je asi 60 000 poštovních schránek. Nejenom Kolabu se věnoval Georg Greve ve své přednášce Open Source: the future for the European institutions (SlideShare) na konferenci DIGITEC 2016, jež proběhla v úterý 29. listopadu v Bruselu. Videozáznam přednášek z hlavního sálu je ke zhlédnutí na Livestreamu.

Ladislav Hagara | Komentářů: 22
2.12. 15:30 | Zajímavý projekt

Společnost Jolla oznámila v příspěvku Case study: Sailfish Watch na svém blogu, že naportovala Sailfish OS na chytré hodinky. Využila a inspirovala se otevřeným operačním systémem pro chytré hodinky AsteroidOS. Použita je knihovna libhybris. Ukázka ovládání hodinek na YouTube.

Ladislav Hagara | Komentářů: 8
2.12. 14:15 | Nová verze

Byla vydána verze 7.1.0 skriptovacího jazyka PHP používaného zejména k vývoji dynamických webových stránek. Jedná se o první stabilní verzi nejnovější větvě 7.1. Přehled novinek v dokumentaci. Podrobnosti v ChangeLogu. K dispozici je také příručka pro přechod z PHP 7.0.x na PHP 7.1.x.

Ladislav Hagara | Komentářů: 4
2.12. 12:55 | Nová verze

Google Chrome 55 byl prohlášen za stabilní. Nejnovější stabilní verze 55.0.2883.75 tohoto webového prohlížeče přináší řadu oprav a vylepšení (YouTube). Opraveno bylo také 36 bezpečnostních chyb. Mariusz Mlynski si například vydělal 22 500 dolarů za 3 nahlášené chyby (Universal XSS in Blink).

Ladislav Hagara | Komentářů: 4
2.12. 11:55 | Pozvánky

Máte rádi svobodný software a hardware nebo se o nich chcete něco dozvědět? Přijďte na 135. sraz spolku OpenAlt, který se bude konat ve čtvrtek 8. prosince od 18:00 v Radegastovně Perón (Stroupežnického 20, Praha 5). Sraz bude tentokrát tématický. Bude retro! K vidění budou přístroje jako Psion 5mx nebo Palm Z22. Ze svobodného hardwaru pak Openmoko nebo čtečka WikiReader. Přijďte se i vy pochlubit svými legendami, nebo alespoň na pivo. Moderní hardware má vstup samozřejmě také povolen.

xkucf03 | Komentářů: 1
2.12. 00:10 | Nová verze

Byla vydána verze 3.2 svobodného systému pro detekci a prevenci průniků a monitorování bezpečnosti počítačových sítí Suricata. Z novinek lze zmínit například podporu protokolů DNP3 a CIP/ENIP, vylepšenou podporu TLS a samozřejmě také aktualizovanou dokumentaci.

Ladislav Hagara | Komentářů: 0
Kolik máte dat ve svém domovském adresáři na svém primárním osobním počítači?
 (32%)
 (24%)
 (29%)
 (7%)
 (5%)
 (3%)
Celkem 771 hlasů
 Komentářů: 50, poslední 29.11. 15:50
Rozcestník
Reklama

Dotaz: "inner join" csv suborov v 2 adresaroch

28.12.2015 15:04 Mike Stuffel
"inner join" csv suborov v 2 adresaroch
Přečteno: 553×

Dobry den,

uz dlhsie sa snazim efektivne vyriesit nasledujuci problem:

 

Do 2 rozdielnych adresarov mi pribudaju CSV subory roznej velkosti ale rovnakeho formatu (su to key-value data). V tomto momente sa bavime asi o 30+ suboroch a celkovej velkosti cca 400GB. Je predpoklad ze objem dat bude do 1.5TB.

 

Potreboval by som efektivne vyriesit "inner join" a vypisat len rovnake riadky zo suborov ulozenych v tychto 2 roznych adresaroch. Nieco ako:

inner_join_csv_files /home/mike/data_A/*.csv /home/mike/data_B/*.csv > rovnake_riadky.csv

 

Momentalne to riesim importom CSV suborov (obsahuju asi 5% duplicit) do 2 roznych tabuliek databazy Postgresql a naslednym SQL INNER JOIN prikazom (do 30 sekund mam vysledok). Toto uz nie je dostacujuce, pretoze import dalsieho CSV suboru trva aj viac ako 48 hodin koli pravidlam nad oboma tabulkami, ktore ignoruju duplicitne inserty (v databaze su len unikatne zaznamy aby sa pouzil index scan a nie sekvencny scan). Navyse cele to bezi len na obycajnom laptope :(.

 

Hladam sposob akym by som mohol usetrit tych 48 hodin pri importe, som ochotny vo vysledku pripustit aj duplicity hlavne nech sa relevantne skrati doba. Je mi jedno aky nastroj alebo technologia sa na to pouzije hlavne nech to cele netrva 48 hodin :). Ak Vas napadne nejaky efektivny sposob ako vyriesit "inner join" CSV suborov v 2 adresaroch budem velmi vdacny.

Odpovědi

BigWrigley avatar 28.12.2015 15:48 BigWrigley | skóre: 32
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch

Nad dvema soubory se da pouzit prikaz comm.

Linux is like a wigwam - no windows, no gates and Apache inside.
28.12.2015 15:58 NN
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Abych si to ujasnil. Mas dva adresare v kazdem ruzne velke csv soubory ktere obsahuji identicka data plus plevel a duplicity a ty chces ziskat cista data porovnanim obsahu. Je to tak? Shodna data jsou rozlozena ruznych v souborech nahodne, nebo se soubory podobaji(ie. je mozne porovnavat dvojici souboru nebo pouze cely balik)?
28.12.2015 16:26 Mike Stuffel
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch

Ano, mam dva adresare s CSV subormi. CSV maju rovnaku strukturu (key-value), ale roznu velkost a rozne nazvy. Chcem ziskat iba riadky, ktore sa nachadzaju v oboch adresaroch sucasne. Zhodne data su rozlozene v suboroch nahodne - teda sa musi porovnavat cely balik (oba adresare) sucasne.

 

Teraz to robim importom do Postgresql a naslednym SQL INNER JOINom

/home/mike/data_A/*.csv  ==> import do DB tabulka_A

/home/mike/data_B/*.csv  ==> import do DB tabulka_B

 

Import je strasne pomaly jeden CSV subor importujem aj 2 dni :(. Hladam teda efektivnejsie riesenie

Josef Kufner avatar 28.12.2015 16:49 Josef Kufner | skóre: 66
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Zkusil bych na dobu importu vypnout indexy. Nebo soubor importovat do nové tabulky bez indexů, a pak data opravit, udělat indexy a teprve potom dál zpracovávat.

Základní myšlenka, data vložit do databáze a pak s tím pracovat, je dobrá, dělal bych to stejně.

Existují ale i jiné databáze než SQL, a možná budou vhodnější pro tento objem dat. Co třeba Cassandra nebo něco podobného?
Hello world ! Segmentation fault (core dumped)
29.12.2015 12:50 Mike Stuffel
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Dakujem za tipy, este sa skusim pohrat so samotnym importom, povypinanim indexov, popripade pred importom rozdelit CSV-cka na mensie a tak importovat....

z NoSQL databaz som skusal Mongo ale tam mi veslovene nesedel koncept map-reduce. S Cassandrou to vyzera onmnoho lepsie podporuje CQL co sa podoba na SQL.
30.12.2015 10:01 Jindřich Makovička | skóre: 13
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Pokud jde o výkon, zkuste místo Cassandry ScyllaDB.
30.12.2015 16:03 Mike Stuffel
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
dakujem za tip urcite sa pozriem aj na to
28.12.2015 17:47 DIK
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Pokud umíš python tak se koukni na analytickou knihovnu panda , umí řešit joiny, duplicity, miss data, obecně se hodí práci s big data a je rychlá... DIK
29.12.2015 13:13 Mike Stuffel
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch

dakujem... toto bude asi presne to co som hladal ale budem sa musiet tomu este povenovat. s pytonom som zatial vobec nerobil, ale podla toho co som v rychlosti nasiel to vyzera celkom jednoducho... spravia sa 2 DataFramy a potom inner join medzi nimy.

http://stackoverflow.com/questions/20906474/import-multiple-csv-files-into-pandas-and-concatenate-into-one-dataframe

http://pandas.pydata.org/pandas-docs/stable/generated/pandas.DataFrame.join.html

http://pandas.pydata.org/pandas-docs/stable/merging.html

28.12.2015 17:58 Kit | skóre: 36 | Brno
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Na tohle používám key->value databáze, například DB4 nebo GDBM. Obsah prvního adresáře nasypu do databáze (jde to podstatně rychleji než u SQL databází) a obsah druhého pak řádek po řádku porovnám.
Komentáře označují místa, kde programátor udělal chybu nebo něco nedodělal.
29.12.2015 12:23 Mike Stuffel
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
presne s tymto pristupom som zacinal (Postgresql), no stal sa neefektivny v momente ked som potreboval takto porovnavat 60+GB CSV-ciek riadok po riadku s databazou. Teraz porovnavanie (inner join) nechavam databaze. Ma tu vyhodu ze vysledok mam do niekolkych sekund ale toto riesenie sa ukazuje tiez ako neefektivne pretoze import CSV suborov do databazy trva prilis dlho.

29.12.2015 14:37 Kit | skóre: 36 | Brno
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
PostgreSQL nemá nic společného s DB4 ani GDBM. Proto jsem navrhl místo PostgreSQL jiné databáze.
Komentáře označují místa, kde programátor udělal chybu nebo něco nedodělal.
30.12.2015 15:56 Mike Stuffel
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Obsah prvního adresáře nasypu do databáze (jde to podstatně rychleji než u SQL databází) a obsah druhého pak řádek po řádku porovnám.
PostgreSQL nemá nic společného s DB4 ani GDBM. Proto jsem navrhl místo PostgreSQL jiné databáze.

Asi som spravne nepochopil. Nieco som som si precital o DB4. Je to cista key-value databaza.

 

Ak ste to mysleli takto:

/home/mike/data_A/*.csv ==> import do DB4 alebo GDBM

/home/mike/data_B/*.csv ==> sekvencne citanie line-by-line + requesty na DB

 

Toto riesenie sa ukazalo ako extremne pomale (mal som maly objem dat). pretoze sa musi robit sekvencne precitanie kazdeho riadku v CSV subore, nasledny request do DB a potom porovnanie ci je zhoda (inner join)

 

Preto som sa rozhodol ze CSV naimportujem do Postgresql, ktory si to sam zaindexuje a urobi jednoduchym SELECTom vsetko za mna - vysledok mam takmer okamzite. No len tento import uz prestava vyhovovat :( pretoze trva aj viac ako 2 dni

30.12.2015 16:01 OldFrog {Ondra Nemecek} | skóre: 25 | blog: Žabákův notes | Praha
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch

No len tento import uz prestava vyhovovat :( pretoze trva aj viac ako 2 dni

Opravdu se podívejte na to předělání importu (jak píšu níže), to je hlavní problém. Změna databáze je krok stranou a původní problém vlastně neřeší.
-- OldFrog
30.12.2015 16:18 Mike Stuffel
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch

suhlasim.... na tom importe je nieco strasne zle.... uvazoval som ci sa da nejako zaobist bez databazy (aby som nemusel robit tak zdlhavy import) tj. nejako urobit "inner join" CSV suborov primo na filesysteme.

Dokonca som chcel pouzit na tuto ulohu sphinxsearch alebo solr, tie si vedia velmi rychlo naindexovat txt subory (podporuju aj delty) a potom takmer okamzite vyhladavat, ale nedokazu urobit "inner join" 2 indexov :(

30.12.2015 16:49 OldFrog {Ondra Nemecek} | skóre: 25 | blog: Žabákův notes | Praha
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Pokud to sphinxsearch/solr zaindexuje strukturovaně, pak to nebude rychlejší. A strukturovaně to potřebujete proto, abyste mohl udělat join. Jednodužšší postup než import do postgres databáze asi nenajdete.

Csvkit sice umí sql dotazy přímo nad cvs, ale těžko to bude rychlejší, než postgres. Také si nejsem jist, zda umí join. Takže bych z rodiny csvkit nástrojů zkusil pouze csvsql - pokud je navržen s ohledem na velká data, může přinést zrychlení, protože možná vhodný postup importu řeší ve vlastní režii.

Nejnadějnější bude otestovat pg_bulkload a pgloader. Tyto nástroje byly vytvořeny speciélně s ohledem na maximální rychlost. Osobně jsem neměl potřebu je zkoušet, vystačím s importem pomoc COPY. Každopádně, pokud importujete INSERTu, používáte nejpomalejší metodu a to i při vypnutých indexech a kontrolách.

Na lehkou váhu bych nebral ani nastavení databáze (Postgres je ve výchozím stavu dost konzervativní) a vyzkoušel SSD disk (dramatické zrychlení IOPS).

Pokud poskytnete vzorek dat, můžu to otestovat i já případně někdo jiný.
-- OldFrog
29.12.2015 13:11 OldFrog {Ondra Nemecek} | skóre: 25 | blog: Žabákův notes | Praha
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Zaměřil bych se na zrychlení toho importu, možná by to šlo zrychlit. Jak import probíhá?
  • singlerow INSERT
  • multirow INSERT
  • COPY
Otestujte nástroje
  • csvkit
  • pg_bulkload
  • pgloader
Podívejte se na další užitečná doporučení na How to speed up insertion performance in PostgreSQL - stackoverflow

I když už jsme u toho, odkad pochází ty csv soubory a jak rychle vznikají?
-- OldFrog
30.12.2015 16:46 Mike Stuffel
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch

import robim cez COPY

copy tabulka_A(key,value) FROM '/home/mike/data_A/fileA.csv' DELIMITER ',' CSV

copy tabulka_B(key,value) FROM '/home/mike/data_B/fileB.csv' DELIMITER ',' CSV

Postgresql ma jednu neprijemnu vlastnost - COPY je jedna trasakcia: ak sa vyskytne duplicita vyhodi hlasku ERROR: duplicate key value violates unique constraint "key", a cely import zlyha. :(

Preto som si napisal pravidlo, ktore ignoruje duplicitny insert do DB. Nieco na tento sposob http://dba.stackexchange.com/questions/30499/optimal-way-to-ignore-duplicate-inserts - a to moze byt kamen urazu.

V podstate sa jedna o exporty z roznych transakcnych systemov, kde sa zaznamenavaju transakcne kroky (data_A) a "podozrive" transakcie (data_B). Tieto vystupy je nutne porovnavat, ked nastane zhoda nasledne manualne vyhodnotit.

/home/mike/data_A/*.csv ==> prirastok je cca 8-10GB za tyzden

/home/mike/data_B/*.csv ==> prirastok je cca 1GB za mesiac

30.12.2015 17:04 OldFrog {Ondra Nemecek} | skóre: 25 | blog: Žabákův notes | Praha
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
A jsme myslím doma. Vypněte kontrolu na duplicitu a natáhněte to i s duplicitama. Podle popisu to vypadá, že ani duplicity kontrolovat nepotřebujete. Pokud ano, můžete duplicity zpracovat po importu až dodatečně - odmazat je, doplnit kontrolu a indexy. Pak teprve dělat dotaz.

Jinak ohledně MERGE a UPSERT - MERGE není implmentovaný, UPSERT je v Postgres 9.5 (netestoval jsem).

Velmi dobrý článek vysvětlující všechny problémy UPSERTu.

Dejte vědět, zda se to zrychlilo.
-- OldFrog
30.12.2015 20:12 OldFrog {Ondra Nemecek} | skóre: 25 | blog: Žabákův notes | Praha
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Zkusil jsem si rychlost importu pro představu. Bez kontrol a indexů vložím milión záznamů za cca 19 sekund. S neunikátním indexem za cca 30sekund. Nastavení databáze je výchozí a s hodnotou shared_buffers = 128MB. Tyhle čísla by měly korespondovat s časem počtem a časem u vás. Korespondují?

Vzorová data mají 312MB a milion řádek:
$ wc -l file_A.csv
1000000 file_A.csv

$ ls -sh file_A.csv
312M file_A.csv

$ head -n3 file_A.csv
2359;c2aa 4ebe 592c 2638 8c8f 5269 2e94 1381 59a9 cadc 2e84 b895 3295 7078 24a6 b512 df94 d803 e5d2 4c15 fc43 c818 49dd 86c5 1c60 90f9 f227 8738 5ef8 95ec e5f4 5288 106a 52b9 dc61 2a34 57a5 bd37 989d fd0e 078f 83b1 a157 b1b0 6399 8b9c a1af 21e3 fa39 7abd 8b9d 0615 bb5f 1afc f302 b0dc de59 18e9 a221 67f4 3a7e 6ea3 891a 619b;
9765;8490 5573 28c2 e229 2519 b612 8745 fee1 e103 2476 3247 ad7d df5e 80ec f5f3 def8 fddc a313 50dd 7b6d 8949 25cd 5fed d7a8 177d b70d d6be 3aa7 8dc0 8df5 de28 34d3 bf03 6413 ca0d 2bb7 f397 a39a 7db0 72aa 7fad de31 4279 9a0b 93f1 4106 74c9 a3fa d1e9 afb7 dadb 0b61 bf0f c674 4c0e 1ecd c0c7 79c3 798d 471c dd5f 8125 dc52 7816;
30671;75c5 f14d f72e 11c0 1833 8248 24b1 a939 38b2 d4d8 3e2e b129 22ad bc0d 2b41 b8da 61ea 18d2 dffb 32ad 83e0 118f 5c81 ae0f 8eb8 a495 a820 d30e 8fe1 a4f6 d234 6e36 a5f8 e17f aa2d 0953 fe34 bced c5bb 63b9 f460 41dc 59ef 8dd4 7043 9a32 54ca d20b 5393 bd72 0fb1 11dc 7980 4ebe eb73 6829 ecf2 b18e 8e52 a3b3 b43a 8ad0 111c b61c;
Databáze
CREATE DATABASE import
  ENCODING = 'UTF8'
  LC_COLLATE = 'cs_CZ.utf8'
  LC_CTYPE = 'cs_CZ.utf8';
GRANT ALL ON DATABASE import TO postgres;
GRANT ALL ON DATABASE import TO public;
Tabulka:
CREATE TABLE t1 (
  key integer,
  value text,
  extra text
);
Bez kontrol a bez indexu:
$ psql -U postgres import -c "TRUNCATE t1;"
TRUNCATE TABLE

$ psql -U postgres import -c "DROP INDEX t1_key_idx;"
ERROR:  index "t1_key_idx" does not exist

$ time psql -U postgres -c "COPY t1(key,value,extra) FROM '/home/ondrej/Test/file_A.csv' DELIMITER ';' CSV;" import
COPY 1000000

real	0m19.562s
user	0m0.003s
sys	0m0.006s
Bez kontrol s indexem:
$ psql -U postgres import -c "TRUNCATE t1;"
TRUNCATE TABLE

$ psql -U postgres import -c "CREATE INDEX t1_key_idx ON t1 USING btree (key);"
CREATE INDEX

$ time psql -U postgres -c "COPY t1(key,value,extra) FROM '/home/ondrej/Test/file_A.csv' DELIMITER ';' CSV;" import
COPY 1000000

real	0m29.042s
user	0m0.002s
sys	0m0.004s
Přelití jedinečných záznamů do jiné tabulky:
$ time psql -U postgres import -c "CREATE TABLE t2 AS SELECT DISTINCT ON(key) * FROM t1;"
SELECT 32768

real	0m15.888s
user	0m0.001s
sys	0m0.008s
Doplnění jedinečného indexu (t2 neobsahuje duplicity, t1 ano):
$ psql -U postgres import -c "CREATE UNIQUE INDEX t2_key_idx ON t2 USING btree (key);"
CREATE INDEX

$ psql -U postgres import -c "DROP INDEX t1_key_idx; CREATE UNIQUE INDEX t1_key_idx ON t1 USING btree (key);"
ERROR:  could not create unique index "t1_key_idx"
DETAIL:  Key (key)=(12063) is duplicated.
Počty řádků v tabulce:
$ psql -U postgres import -c "SELECT count(*) FROM t1;"
  count  
---------
 1000000
(1 řádka)

$ psql -U postgres import -c "SELECT count(*) FROM t2;"
 count 
-------
 32768
(1 řádka)
Verze databáze:
$ psql -U postgres import -c "SELECT version();"
                                                   version                                                   
-------------------------------------------------------------------------------------------------------------
 PostgreSQL 9.4.5 on x86_64-redhat-linux-gnu, compiled by gcc (GCC) 5.1.1 20150618 (Red Hat 5.1.1-4), 64-bit
(1 řádka)
A s Potgres 9.5.rc1 a UPSERT:
$ psql -U postgres -h localhost -p 5434 import -c "TRUNCATE TABLE t2;"
TRUNCATE TABLE

$ psql -U postgres -h localhost -p 5434 import -c "DROP INDEX IF EXISTS t2_key_idx;"
DROP INDEX

$ psql -U postgres -h localhost -p 5434 import -c "CREATE UNIQUE INDEX t2_key_idx ON t2 USING btree (key);"
CREATE INDEX

$ time psql -U postgres -h localhost -p 5434 import -c "INSERT INTO t2 SELECT * FROM t1 ON CONFLICT (key) DO NOTHING;"
INSERT 0 32768

real	0m6.932s
user	0m0.005s
sys	0m0.006s

$ psql -U postgres -h localhost -p 5434 import -c "SELECT version();"
                                                  version                                                  
-----------------------------------------------------------------------------------------------------------
 PostgreSQL 9.5rc1 on x86_64-pc-linux-gnu, compiled by gcc (GCC) 4.1.2 20080704 (Red Hat 4.1.2-55), 64-bit
(1 řádka)
-- OldFrog
30.12.2015 23:28 OldFrog {Ondra Nemecek} | skóre: 25 | blog: Žabákův notes | Praha
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Ještě jsem to zkusil pomocí pg_bulkload a pgloader. Ostatní parametry jsou stejné, Postgres je 9.5.rc1.

Pomocí pg_bulkload:
$ time pg_bulkload -h localhost -p 5434 -U postgres -d import file_A.ctl
NOTICE: BULK LOAD START
NOTICE: BULK LOAD END
	0 Rows skipped.
	1000000 Rows successfully loaded.
	0 Rows not loaded due to parse errors.
	0 Rows not loaded due to duplicate errors.
	0 Rows replaced with new rows.

real	0m10.887s
user	0m0.002s
sys	0m0.004s
A pomocí pgloader:
$ pgloader --type csv --field key --field value --field extra --with "drop indexes" --with "disable triggers" --with "fields terminated by ';'" file_A.csv postgres://postgres:***@localhost:5434/import?tablename=file_A
2015-12-30T22:56:31.075000+01:00 LOG Main logs in '/tmp/pgloader/pgloader.log'
2015-12-30T22:56:31.079000+01:00 LOG Data errors in '/tmp/pgloader/'
       table name       read   imported     errors      total time       read      write
-----------------  ---------  ---------  ---------  --------------  ---------  ---------
            fetch          0          0          0          0.011s                     
-----------------  ---------  ---------  ---------  --------------  ---------  ---------
           file_a    1000000    1000000          0         47.886s    47.148s   18.913s
-----------------  ---------  ---------  ---------  --------------  ---------  ---------
Total import time    1000000    1000000          0         48.109s    47.148s   18.913s
-- OldFrog
Aleš Janda avatar 29.12.2015 13:17 Aleš Janda | skóre: 21 | blog: kýblův blog | Kralupy nad Vltavou
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Pokud mají být ty řádky opravdu stejné (ve všech sloupcích; pak je otázka, k čemu to je), stačilo by

cat /home/mike/data_A/*.csv /home/mike/data_B/*.csv | LANG=C sort | uniq -d

(vezmeš všechno, seřadíš, vypíšeš jen duplicitní)

Pokud by se to mělo dělat opakovaně nad stejnýma souborama, pak se vyplatí je seřadit předem (někam vedle) a potom pomocí

LANG=C sort -m soubor /home/mike/data_A/*.serazeno.csv /home/mike/data_B/*.serazeno.csv | uniq -d

už seřazené soubory zmergoat a zase vypsat duplicity.

Pokud bys nechtěl vyloženě duplicitní řádky, ale duplicitní jen některé klíče, tak bych ty klíče dal jako první sloupec, seřadil, zmergoval a nějakým vlastním skriptem rozhodl, jestli ty řádky teda duplicitní jsou nebo ne a podle toho vypsal :-) Nicméně to už je trivialita, to hlavní (seřazení) už budeš mít hotové.

To LANG=C je dobré uvádět, pokud nechceš vyloženě třídit podle nějakých lokálních specifikací, je to pak rychlejší.

Všechno toto všechno bude trvat řádově méně než 48 hodin :-)
29.12.2015 14:41 dustin | skóre: 60 | blog: dustin
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Nevím, jak jsou uniq a sort napsané, snad jim bude stačit paměť...
29.12.2015 14:53 Lukáš Džunko | skóre: 39 | blog: Jooky | Bratislava
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
urcite nebude :) ... tu sa nebavime o par MB suboroch, ale cca 400GB. V tom pripade nie je ina moznost ako pouzit databazu. Ked je problem take mnozstvo dat dostat do databazy v rozumnom case, tak je nejaky problem so samontym importom a to treba poriesit. Ako uz bolo spomenute. Vypnut indexy, natlacit data do databazy. Zapnut indexy a potom sa moze robit akykolvek select nad datami. Dalsie pridavanie je uz lepsie riesit "prihadzovanim" novych suborov, nie znova celym importom. Ak to nepojde idealne, tak treba osetrit aj tento inkrementalny import (vypinanim klucov, spravit to ako jednu transakciu, etc.).
Aleš Janda avatar 29.12.2015 18:30 Aleš Janda | skóre: 21 | blog: kýblův blog | Kralupy nad Vltavou
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Paměť stačit bude, neboj :-)

uniq nepotřebuje paměť žádnou (porovnává max. dva řádky za sebou), sort si pak setříděné mezivýsledky, které se mu nevejdou do paměti, ukládá do tempu. Tj. v tempu musí být ideálně tolik místa, jak je velký zdrojový soubor.

Sesortit 400 GB tedy není problém, pokud je dost místa na disku. Na disku je zřejmě místa dost, když teď těch 400 GB cpe do databáze, kde jsou i indexy, režie apod.

Pro jednorázové použití by měl být sort + uniq o dost efektivnější než databáze. Jednak kvůli absenci dodatečné režie (parsování dotazu apod.), jednak proto, že databáze obecně nejsou moc optimalizovány pro import a dá se s tím dělat jen hodně málo (před časem jsem řešil zrovna pro PostgreSQL).

Řešení sort + uniq (v trochu jiném podání, volám to opakovaně) mám použito na jednom webu, kde se to sortí denně, cca 100 GB dat.
29.12.2015 19:54 Lukáš Džunko | skóre: 39 | blog: Jooky | Bratislava
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
o tom, ze si sort uklada medzivysledky do tempu som nevedel, no stale to neriesi problem :) ... SQL INNER JOIN sa cez sort spravit neda.
30.12.2015 17:20 Mike Stuffel
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch

takto to funguje teraz. Dostanem novy CSV subor a ten naimportujem do databazy.

CREATE TABLE tabulka_A ( key varchar(16) PRIMARY KEY, value varchar(128) );

vypinanie/zapinanie primarneho kluca je vhodne, kym mam zarucene ze v CSV suboroch nebudu duplicity (teraz je ich cca 5%) - v databaze by som ich nechcel mat. Pri importe chcem mat zapnuty primarny key koli duplicitam.

ak by som pred importom vypol primarny kluc riskoval by som ze v databaze by boli duplicity a nesiel by potom zapnut. Musel by som vsetky duplicity mazat rucne a az tak ho zapnut (pain in ass).

30.12.2015 18:29 OldFrog {Ondra Nemecek} | skóre: 25 | blog: Žabákův notes | Praha
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Ty duplicity si můžete zpracovat i dodatečně. Postgres 9.5 umí výše zmiňovaný UPSERT, takže to nalejte třeba do jedné tabulky bez kontroly duplicity a pak přelejte do cílové tabulky s ON CONFLICT DO NOTHING:
CREATE TABLE t2 ...;
INSERT INTO t2 AS SELECT * FROM t1 ON CONFLICT (...) DO NOTHING;
Implementace v databázi bude rychlejší než vaše funkce (kdoví jestli je správně implementovaná). Anebo:
CREATE TABLE t2 AS SELECT DISTINCT ON(...) FROM t1;
Chce si to s tím trochu pohrát. Kolik řádků má vlastně těch zmiňovaných 400GB?
-- OldFrog
31.12.2015 09:08 Mike Stuffel
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Chce si to s tím trochu pohrát. Kolik řádků má vlastně těch zmiňovaných 400GB?
jj budem sa tomu musiet povenovat a tiez potunit konfigurak - mam teraz defaultny. Momentalne je tam 4184023358 riadkov. Ak sa objem bude blizit ku 1.5TB budem sa musiet zamysliet ako pokracovat dalej. Myslite ze Postgresql je vhodny na spracovanie aj takto velkych (key-value) dat? Na SQL databazach sa mi paci, ze behom kratkej chvile a velmi jednoduchym sposobom dokazem dostat pozadovane data.
31.12.2015 09:57 NN
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Uvazoval bych o tom, zda zminovane transakcni systemy, nemuzou ukladat do databaze 'inline' bez tohoto manualniho mezikroku.
Josef Kufner avatar 31.12.2015 14:08 Josef Kufner | skóre: 66
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Uvažoval jsi o způsobu, jak se řádků zbavit? Spočítat si nějaký mezivýsledek a o pár řádů zmenšit množství dat pro další zpracování.
Hello world ! Segmentation fault (core dumped)
31.12.2015 14:11 OldFrog {Ondra Nemecek} | skóre: 25 | blog: Žabákův notes | Praha
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Hmm, 4184023358 řádků je dost. Pokud bych aproximoval svoje testy, tak by se tento počet řádků importoval 10 (pg_bulkload) až 24 (COPY) hodin. Pokud by byly databáze i zdrojová data v ramdisku, bylo by to asi polovic (tuto variantu jsem ale v testech výše neuváděl).

Doporučil bych se zamyslet, zda by bylo možné provádět importy průběžně. Pokud Vám přibude 10GB týdně, tak těchto 10GB budete importovat asi půl hodiny, což už je v pohodě.

Jinými slovy - upravte postup zpracování tak, aby se nemuselo pracovat s takovým objemem naráz. To znamená zpracovávat csv soubory častěji (jednoduše nasadit logrotate?) anebo logovat do databáze rovnou (asi větší zásah postupu). To jsou systémová řešení. Postgres má limit 32TB na tabulku, limit na velikost databáze ani počet řádků v tabulce není řádný. Pokud přikoupíte RAM a SSD disk, vystačíte s tím hodně dlouho.

Uvědomte si, že alternativní databázové systémy nejsou zázračně rychlejší, jsou pouze lépe škálovatelné (pro více procesorů, více počítačů, s paralelizací a podporou pro dotazy nad několikařádově větším objemem dat). Vy máte jen jeden počítač a objem dat, který by pro relační databázi neměl být zas takový problém.

Ohledně použití csv jako storage pro databázi - možná to jde, ale dotazy nad těmi daty budou asi dost pomalé, takže ve výsledku to může ještě pomalejší.
-- OldFrog
20.1. 15:06 Mike Stuffel
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Rad by som sa podakoval vsetkym ktori prispeli radou, najma p. OldFrog {Ondra Nemecek}. Po testoch navrhovanych rieseni sa ukazalo, ze uzkym hrdlom je hardware. Po prechode na SSD + dokupenie RAM + migracia a tuning Postgresql 9.5 sa doba importu vyznamne znizila na cca 6-8 hodin.
20.1. 18:25 OldFrog {Ondra Nemecek} | skóre: 25 | blog: Žabákův notes | Praha
Rozbalit Rozbalit vše Re: "inner join" csv suborov v 2 adresaroch
Tak to jsem rád, že to šlape :-)
-- OldFrog

Založit nové vláknoNahoru

Tiskni Sdílej: Linkuj Jaggni to Vybrali.sme.sk Google Del.icio.us Facebook

ISSN 1214-1267   www.czech-server.cz
© 1999-2015 Nitemedia s. r. o. Všechna práva vyhrazena.