BG Development


Страници: (3) [1] 2 3   ( Първото ново мнение ) Reply to this topicStart new topicStart Poll

> Как е най-ефективно
Gamma Goblin
Публикувано на: 23-07-2019, 20:40
Quote Post



Име:
Група: Потребител
Ранг: Почетен член

Мнения: 2690
Регистриран на: 21.02.18



Quiz of the day:
----

CODE
+----+------+
| ID | Shit |
+----+------+
|  1 | s1   |
|  2 | s2   |
|  3 | s3   |
+----+------+


Как най-ефективно мога да намеря всички елементи от даден списък които *не са* в тая таблица ? Списъка е много голям, таблицата също icon_smile.gif След кратки тестове най-ефективното което измислих е с временна таблица, но малко не ме кефи icon_smile.gif

Това мнение е било редактирано от Gamma Goblin на 23-07-2019, 20:50


--------------------
https://www.rust-lang.org/
---
Хора, които са прекалено умни, за да се занимават с политика, са наказани да бъдат управлявани от глупаци.
---
Life is hard; it's harder when you're stupid.
---
Black metal is like coffee. You have to learn to drink it but when you get used to it, you just want it darker and darker
PMEmail PosterUsers Website
Top
Gosheto
Публикувано на: 23-07-2019, 21:05
Quote Post



Име:
Група: Потребител
Ранг: Посетител

Мнения: 80
Регистриран на: 07.05.07



Това..?

sqlfiddle
PMEmail Poster
Top
Gamma Goblin
Публикувано на: 23-07-2019, 21:13
Quote Post



Име:
Група: Потребител
Ранг: Почетен член

Мнения: 2690
Регистриран на: 21.02.18



QUOTE (Gosheto @ 23-07-2019, 21:05)
Това..?

sqlfiddle

Нещо такова, но трябва да мога да си подавам нещата от списъка като променлив брой параметри, защото не знам кои и колко са предварително.

За сега най-бързо е с

CODE
explain analyze select c.guid from checker c
where not exists (select 1 from something s where s.guid = c.guid);


Като checker е временна таблица с тъпо име. Като при мен е двойно по-бързо от варианта с EXCEPT.

Това мнение е било редактирано от Gamma Goblin на 23-07-2019, 21:14


--------------------
https://www.rust-lang.org/
---
Хора, които са прекалено умни, за да се занимават с политика, са наказани да бъдат управлявани от глупаци.
---
Life is hard; it's harder when you're stupid.
---
Black metal is like coffee. You have to learn to drink it but when you get used to it, you just want it darker and darker
PMEmail PosterUsers Website
Top
Gamma Goblin
Публикувано на: 23-07-2019, 21:13
Quote Post



Име:
Група: Потребител
Ранг: Почетен член

Мнения: 2690
Регистриран на: 21.02.18



CODE

devdb=> explain analyze select c.guid from checker c
where not exists (select 1 from something s where s.guid = c.guid);
                                                       QUERY PLAN                                                        
---------------------------------------------------------------------------------------------------------------------------
Hash Anti Join  (cost=279.00..313.74 rows=680 width=32) (actual time=6.185..6.779 rows=1000 loops=1)
  Hash Cond: ((c.guid)::text = (s.guid)::text)
  ->  Seq Scan on checker c  (cost=0.00..23.60 rows=1360 width=32) (actual time=0.021..0.392 rows=2001 loops=1)
  ->  Hash  (cost=154.00..154.00 rows=10000 width=4) (actual time=5.599..5.599 rows=10000 loops=1)
        Buckets: 16384  Batches: 1  Memory Usage: 489kB
        ->  Seq Scan on something s  (cost=0.00..154.00 rows=10000 width=4) (actual time=0.018..2.620 rows=10000 loops=1)
Planning Time: 0.211 ms
Execution Time: 6.916 ms



CODE
devdb=> explain analyze select c.guid from checker c
except select s.guid from something s;
                                                          QUERY PLAN                                                            
---------------------------------------------------------------------------------------------------------------------------------
HashSetOp Except  (cost=0.00..376.40 rows=200 width=36) (actual time=10.639..10.963 rows=1000 loops=1)
  ->  Append  (cost=0.00..348.00 rows=11360 width=36) (actual time=0.025..7.471 rows=12001 loops=1)
        ->  Subquery Scan on "*SELECT* 1"  (cost=0.00..37.20 rows=1360 width=36) (actual time=0.024..0.890 rows=2001 loops=1)
              ->  Seq Scan on checker c  (cost=0.00..23.60 rows=1360 width=32) (actual time=0.020..0.399 rows=2001 loops=1)
        ->  Subquery Scan on "*SELECT* 2"  (cost=0.00..254.00 rows=10000 width=8) (actual time=0.017..4.780 rows=10000 loops=1)
              ->  Seq Scan on something s  (cost=0.00..154.00 rows=10000 width=4) (actual time=0.016..2.641 rows=10000 loops=1)
Planning Time: 0.128 ms
Execution Time: 11.257 ms
(8 rows)


--------------------
https://www.rust-lang.org/
---
Хора, които са прекалено умни, за да се занимават с политика, са наказани да бъдат управлявани от глупаци.
---
Life is hard; it's harder when you're stupid.
---
Black metal is like coffee. You have to learn to drink it but when you get used to it, you just want it darker and darker
PMEmail PosterUsers Website
Top
dvader
Публикувано на: 23-07-2019, 22:50
Quote Post


Group Icon
Име:
Група: VIP
Ранг: Почетен член

Мнения: 4545
Регистриран на: 12.07.05



Временната таблица изисква отделно куери - така нещата а) не са атомични, б) не са нишко-безопасни.

Вместо временна таблица - WITH ... SELECT
или направо някой INNER JOIN


--------------------
I find your lack of faith disturbing
PM
Top
code2
Публикувано на: 24-07-2019, 07:10
Quote Post



Име:
Група: Потребител
Ранг: Активен

Мнения: 277
Регистриран на: 11.06.16



Ако въпросът ти не е теоретичен, тогава защо просто не сортираш таблицата и списъка по търсения елемент и да почнеш да ги четеш паралелно с две заявки? Това би трябвало да е достатъчно ефективно.

CODE

таблица  списък
 t        l
 s1       s3
 s2       s6
 s3       s7
 s4
 s5
 s7


Алгоритъм:
CODE

while
{if(t==l) {чети ново t и l; няма някое от тях?break;  continue}
 if(t<l)  {резултат t; чети ново t; няма такова?break; continue}
 if(t>l)  {чети ново l; няма такова?break; continue}
}
имаме t?
{while
 {резултат t; чети ново t; няма такова?break;
 }
}


Това е на принципа на merge sort.

Това мнение е било редактирано от code2 на 24-07-2019, 07:11
PMEmail Poster
Top
Gamma Goblin
Публикувано на: 24-07-2019, 07:29
Quote Post



Име:
Група: Потребител
Ранг: Почетен член

Мнения: 2690
Регистриран на: 21.02.18



@code2, това ще е брутално бавно


--------------------
https://www.rust-lang.org/
---
Хора, които са прекалено умни, за да се занимават с политика, са наказани да бъдат управлявани от глупаци.
---
Life is hard; it's harder when you're stupid.
---
Black metal is like coffee. You have to learn to drink it but when you get used to it, you just want it darker and darker
PMEmail PosterUsers Website
Top
Gamma Goblin
Публикувано на: 24-07-2019, 07:31
Quote Post



Име:
Група: Потребител
Ранг: Почетен член

Мнения: 2690
Регистриран на: 21.02.18



QUOTE (dvader @ 23-07-2019, 22:50)
Временната таблица изисква отделно куери - така нещата а) не са атомични, б) не са нишко-безопасни.

Вместо временна таблица - WITH ... SELECT
или направо някой INNER JOIN

QUOTE
а) не са атомични

не е проблем

QUOTE
не са нишко-безопасни.
защо ? Временната таблица съяествува само в рамките на връзката. Като затвориш conenction-a и тя изчезва. Тоест всяка връзка си има собствена временна таблица и една връзка не може да види временната таблица на друга.


--------------------
https://www.rust-lang.org/
---
Хора, които са прекалено умни, за да се занимават с политика, са наказани да бъдат управлявани от глупаци.
---
Life is hard; it's harder when you're stupid.
---
Black metal is like coffee. You have to learn to drink it but when you get used to it, you just want it darker and darker
PMEmail PosterUsers Website
Top
Gamma Goblin
Публикувано на: 24-07-2019, 08:29
Quote Post



Име:
Група: Потребител
Ранг: Почетен член

Мнения: 2690
Регистриран на: 21.02.18



Поради някаква прикина не ми е ползвало hash индекса icon_sad.gif Докато на fiddle-a го ползва и с временна таблица мачка: https://www.db-fiddle.com/f/wR1jaFfTZUnejmWZTMSwxY/2


--------------------
https://www.rust-lang.org/
---
Хора, които са прекалено умни, за да се занимават с политика, са наказани да бъдат управлявани от глупаци.
---
Life is hard; it's harder when you're stupid.
---
Black metal is like coffee. You have to learn to drink it but when you get used to it, you just want it darker and darker
PMEmail PosterUsers Website
Top
code2
Публикувано на: 24-07-2019, 08:40
Quote Post



Име:
Група: Потребител
Ранг: Активен

Мнения: 277
Регистриран на: 11.06.16



QUOTE (Gamma Goblin @ 24-07-2019, 07:29)
@code2, това ще е брутално бавно

Добре тогава. Ето ти по-добро решение:
CODE

create table tbl1(id INT,name VARCHAR(50),city VARCHAR(25));
create table tbl2 like tbl1;
insert into tbl1 values (1,'adam', 'eden'), (2, 'eva', 'eden');
insert into tbl2 values (3,'adam', 'eden'), (4, 'pedro', 'alexandria');

SELECT * FROM (SELECT 1 as tb_id,name,city from tbl1 UNION SELECT 2 as tb_id,name,city from tbl2) as a GROUP BY name HAVING (count(*)=1)AND(tb_id=1);

Това което направих е просто да модифицирам за нуждите вече дадено решение в stackoverflow:
https://dba.stackexchange.com/questions/102...data-repetition
Първите 4 реда в горната заявка са само за да има пълна демонстрация, както е в оригиналния цитиран отговор.
PMEmail Poster
Top
1 потребители преглеждат тази тема в момента (1 гости, 0 анонимни потребители)
Потребители, преглеждащи темата в момента:

Topic Options Страници: (3) [1] 2 3  Reply to this topicStart new topicStart Poll

 


Copyright © 2003-2019 | BG Development | All Rights Reserved
RSS 2.0