2010-06-25 21 views
7

tek sıra sütunlar halinde birden çok satır dönüştürme MySQL:i sütunlu bir detayı tablo var

  • user_id int
  • kod int
  • değeri int

Ve kurmak istiyorum gibi görünen bir özet tablo:

  • user_id int
  • DEĞERİa KESİNLİK
  • VALUE Milyar Ayrıntılar tablosundaki

int int, DEĞERİa KESİNLİK kodu 5, söylemek karşılık olur ve VALUE Milyar söylemek karşılık olur, kod 6, bu yüzden böyle bir şey arıyorum:

özete ekle (user_id, valueA, valueB) VALUES (SELECT ??? detaylardan);

Tabii ki sorun "özet" tablosundaki bir satırı doldurmak için "ayrıntılar" tablosundan birden fazla satıra bakıyorum.

Örneğin, ben detaylar aşağıdaki satırlar varsa:

1 100 200 
2 1000 2000 

Herhangi fikirler: Ben özet tablosunda aşağıdaki ile bitirmek istiyorum

1 5 100 
1 6 200 
2 5 1000 
2 6 2000 

? Eğer kodları kolay bir set varsa

+0

5 soru, hiçbir kabul cevap, diğer insanların sorularına 0 cevap. Bunun bir topluluk odaklı site olduğunu ve bir firmanın destek forumunu bilmediğini biliyorsunuz değil mi? – Anax

cevap

8

MySQL GROUP BY ve VAKA ifadelerin bir arada kullanmak bırakır MİL/UNPIVOT sözdizimi, yok:

INSERT INTO SUMMARY 
    (user_id,valueA,valueB) 
    SELECT d.user_id, 
     MAX(CASE WHEN d.code = 5 THEN d.value ELSE NULL END), 
     MAX(CASE WHEN d.code = 6 THEN d.value ELSE NULL END), 
    FROM DETAILS d 
GROUP BY d.user_id 
+0

Bu, en kullanışlı bulduğum yanıttır. Başa çıkmak için büyük bir masa vardı ve bu yeterli bir şekilde gerçekleştirildi. – Jack

+0

Harika, bu benim SQL'lerden biri için aradığım şey. Teşekkürler! – hese

+0

Fantasic, bu bölümü değiştirdi: Bir kullanıcının kategorisinin belirli bir arama kategorisiyle tam olarak eşleşip eşleşmediğini belirlemek için bir bool değerini döndürmek için MAX (CASE WHEN d.code = 5 DİZ d.value ELSE NULL END). aile kategorisi. – nealio82

0

(sadece 5 söylemek ve 6) Böyle bir şey yapabileceğini:

SELECT details.user_id, code5.value, code6.value 
FROM details JOIN 
    (SELECT user_id, value FROM details WHERE code = 5) AS code5 USING(user_id) 
    JOIN 
    (SELECT user_id, value FROM details WHERE code = 6) AS code6 USING(user_id); 

Sen kodları olarak gerekli değilse bağlı olarak JOIN s değiştirmeniz gerekebilir 1 ila 1 ilişki (yani LEFT JOIN s).

Büyük bir kod kümeniz varsa, bir imleç, kodlarınızın bir sonuç kümesi üzerinde veya farklı bir teknoloji kullanarak (ör. PHP betiği) benzer bir sorguyu çalıştırır.

2
insert into summary (user_id,valueA,valueB) 
SELECT a.user_id, a.value, b.value 
from details a 
join details b on a.user_id = b.user_id 
WHERE a.code = 5 and b.code = 6; 

dikkat: user_id + kod benzersiz değilse Birden özeti sütunları ile sona erecek.

DÜZENLEME:

insert into summary (user_id,valueA,valueB) 
select u.user_id, ifnull(a.value,0), ifnull(b.value,0) 
from (select distinct user_id from details /* where code in (5,6) */) u 
left join details a on a.user_id = u.user_id and a.code = 5 
left join details b on b.user_id = u.user_id and b.code = 6 
+0

Teşekkürler! Ama aslında 3 değere ihtiyacım vardı ve yukarıdakileri “bariz” şekilde değiştirdim (başka bir birleşim ekleyerek) ve işe yaradı; ama şu an sahip olduğum problem, herhangi bir kullanıcının satırlardan herhangi birini kaçırmaması durumunda (ör. A ve B var, fakat C eksikse) o kullanıcı için bir satır yok.Bunun yerine, ayrıntılar tablosundaki eksik değerler için 0'lı bir satır görmek istiyorum. Bunun hakkında bir fikrin var mı? – Jack

+0

daha sonra sol birleştirmeyi kullanın, bkz. "Düzenleme" –