2016-04-10 15 views
5

Wyobraźmy sobie tabelę, która wygląda tak:Jak mogę SUMIĆ odrębne rekordy w bazie danych Postgres, gdzie znajdują się zduplikowane rekordy?

table with duplicate data

SQL, aby uzyskać te dane właśnie SELECT * Pierwsza kolumna to „ROW_ID” drugi „id” - który to identyfikator zamówienia i trzecia to "całkowita" - która jest przychodem.

Nie wiem, dlaczego w bazie danych znajdują się duplikaty wierszy, ale gdy wykonuję SUM (suma), uwzględniam drugi wpis w bazie danych, mimo że identyfikator zamówienia jest taki sam, co powoduje liczby powinny być większe niż w przypadku wybrania odrębnego (id), całkowitego - eksportu do programu Excel, a następnie sumowania wartości ręcznie.

Moje pytanie brzmi - w jaki sposób mogę SUMOWAĆ tylko dla różnych identyfikatorów zamówień, aby uzyskać taki sam przychód, jak w przypadku eksportu do programu Excel, który wyróżniałby każdy wiersz identyfikatora zamówienia?

Z góry dzięki!

+0

http://meta.stackoverflow.com/questions/285551/why-may-i-not-upload -images-of-code-on-so-when-asking-a-question/285557 # 285557 –

Odpowiedz

1

Można spróbować coś takiego (ze swoim przykładzie):

Tabela

create table test (
    row_id int, 
    id int, 
    total decimal(15,2) 
); 

insert into test values 
(6395, 1509, 112), (22986, 1509, 112), 
(1393, 3284, 40.37), (24360, 3284, 40.37); 

Zapytanie

with distinct_records as (
    select distinct id, total from test 
) 

select a.id, b.actual_total, array_agg(a.row_id) as row_ids 
from test a 
inner join (select id, sum(total) as actual_total from distinct_records group by id) b 
    on a.id = b.id 
group by a.id, b.actual_total 

Wynik

| id | actual_total | row_ids | 
|------|--------------|------------| 
| 1509 |   112 | 6395,22986 | 
| 3284 |  40.37 | 1393,24360 | 

Wyjaśnienie

Nie wiemy, jakie są powody, dla zamówień i sumy pojawić więcej niż jeden raz z innym row_id. Zatem używając wspólnego wyrażenia tabelowego (CTE), używając fraza with ..., otrzymujemy wyraźny identyfikator i sumę.

W ramach CTE używamy tych odrębnych danych do sumowania. Łączymy identyfikator w oryginalnej tabeli z agregacją na różnych wartościach. Następnie rozdzielamy przecinkami dane row_ids, aby informacje wyglądały czystsze.

SQLFiddle przykład

http://sqlfiddle.com/#!15/72639/3

+0

Dziękuję! Spróbuję tego teraz! Bardzo doceniane !!! –

+0

Czy ta odpowiedź pomogła Ci @KatieF? – zedfoxus

0

Jeśli możemy ufać, że całkowita za 1 zamówienia jest rzeczywiście 1 rzędzie. Możemy wyeliminować duplikaty w pod-zapytaniu, wybierając MAX kolumny PK id. Przykład:

CREATE TABLE test2 (id int, order_id int, total int); 

insert into test2 values (1,1,50); 
insert into test2 values (2,1,50); 
insert into test2 values (5,1,50); 
insert into test2 values (3,2,100); 
insert into test2 values (4,2,100); 

select order_id, sum(total) 
    from test2 t 
    join (
    select max(id) as id 
     from test2 
     group by order_id) as sq 
    on t.id = sq.id 
    group by order_id 

sql fiddle

5

proste - wystarczy podzielić przez ilość:

select id, sum(total)/count(id) 
from orders 
group by id 

obsługuje również dowolny poziom powielania, np trzy powtórzenia itd.

+0

To jest takie sprytne! – rat

1

Można użyć DISTINCT w swoich zagregowanych funkcji:

SELECT id, SUM(DISTINCT total) FROM orders GROUP BY id 

Dokumentacja tutaj: https://www.postgresql.org/docs/9.6/static/sql-expressions.html#SYNTAX-AGGREGATES

+0

Nie zamierzam tego usuwać, ale tak naprawdę jest * źle *. Gdy używasz 'distinct' wewnątrz funkcji agregującej, otrzymuje ona odrębne wartości kolumny, więc jeśli masz jakieś odrębne zamówienia o tej samej wartości, twoja suma będzie niedokładna. 'Suma (total)/count (id)' wygrywa to. –

Powiązane problemy