2011-02-03 19 views
9

यह शायद आसान है, यहाँ मेरी क्वेरी है है:निकाला जा रहा है डुप्लिकेट (बस नहीं "अलग का उपयोग")

SELECT DISTINCT U.NAME, P.PIC_ID 
FROM USERS U, PICTURES P, POSTINGS P1 
WHERE U.EMAIL_ID = P1.EMAIL_ID AND P1.PIC_ID = P.PIC_ID AND P.CAPTION LIKE '%car%'; 

लेकिन यह केवल डुप्लिकेट को हटा देगा जहां एक पंक्ति दोनों एक ही u.name और है p.pic_id। मैं इसे इसलिए चाहता हूं यदि नामों के कोई डुप्लीकेट हैं, तो यह अन्य पंक्तियों को छोड़ देता है। यह एक अजीब सवाल है, लेकिन आम तौर पर, मैं चयन खंड के एक कॉलम के लिए अलग कैसे लागू कर सकता हूं?

+1

एकाधिक P.PIC_ID में से कौन सा आप एकल U.NAME के ​​साथ चाहते हैं? –

उत्तर

15

मनमाने ढंग से न्यूनतम PIC_ID रखने के लिए चुनने। इसके अलावा, अंतर्निहित शामिल वाक्यविन्यास का उपयोग करने से बचें।

SELECT U.NAME, MIN(P.PIC_ID) 
    FROM USERS U 
     INNER JOIN POSTINGS P1 
      ON U.EMAIL_ID = P1.EMAIL_ID 
     INNER JOIN PICTURES P 
      ON P1.PIC_ID = P.PIC_ID 
    WHERE P.CAPTION LIKE '%car%' 
    GROUP BY U.NAME; 
+0

व्यवसाय के मामले के आधार पर, आप या तो MIN या MAX का उपयोग कर सकते हैं (स्पष्ट रूप से दोनों एक ही समय में नहीं)। – Naufal

1

आप क्वेरी क्या मूल्य अन्य स्तंभों, MIN या MAX उपयुक्त विकल्प की तरह लग के लिए लेने के लिए बताने के लिए की जरूरत है।

SELECT 
    U.NAME, MIN(P.PIC_ID) 
FROM 
    USERS U, 
    PICTURES P, 
    POSTINGS P1 
WHERE 
    U.EMAIL_ID = P1.EMAIL_ID AND 
    P1.PIC_ID = P.PIC_ID AND 
    P.CAPTION LIKE '%car%' 
GROUP BY 
    U.NAME; 
+1

मुझे नहीं लगता कि वह यही चाहता है। मुझे लगता है कि वह सभी तस्वीरें चाहता है, लेकिन ऐसे मामलों में जहां एक उपयोगकर्ता के पास कई चित्र हैं, वह नहीं चाहता कि उपयोगकर्ता का नाम सूची में दोहराया जाए। – KeithS

+1

अंतर्निहित शामिल वाक्यविन्यास के उपयोग को प्रोत्साहित न करें। यदि आप उसे दिखा रहे हैं कि चीजें कैसे करें, तो उसे दिखाएं कि चीजों को सही तरीके से कैसे करें। – HLGEM

+0

@HLGEM, मेरे अपने ज्ञान के लिए, अंतर्निहित वाक्यविन्यास के साथ क्या गलत है? कुछ ओडीबीसी ड्राइवर (जैसे टाइगरलॉग के डी 3) केवल अंतर्निहित वाक्यविन्यास का समर्थन करते हैं। –

0

अगर मैं तुम्हें सही ढंग से समझ, आप एक ही नाम (और उनके अलग अलग आईडी) ऐसी है कि उनके नाम एक बार तालिका में की तुलना में अधिक होता है के साथ सभी चित्रों की एक सूची चाहते हैं। मुझे लगता है कि इस चाल करना होगा:

SELECT U.NAME, P.PIC_ID 
FROM USERS U, PICTURES P, POSTINGS P1 
WHERE U.EMAIL_ID = P1.EMAIL_ID AND P1.PIC_ID = P.PIC_ID AND U.Name IN (
SELECT U.Name 
FROM USERS U, PICTURES P, POSTINGS P1 
WHERE U.EMAIL_ID = P1.EMAIL_ID AND P1.PIC_ID = P.PIC_ID AND P.CAPTION LIKE '%car%'; 
GROUP BY U.Name HAVING COUNT(U.Name) > 1) 

मैं इसे क्रियान्वित नहीं किया है, इसलिए एक सिंटैक्स त्रुटि या वहाँ दो हो सकता है।

+1

निहित शामिल वाक्यविन्यास के उपयोग को प्रोत्साहित न करें। यदि आप उसे दिखा रहे हैं कि चीजें कैसे करें, तो उसे दिखाएं कि चीजों को सही तरीके से कैसे करें। – HLGEM

+0

मैंने इसे माना, लेकिन मैं उस समस्या को हल करना चाहता था जिस पर वह काम कर रहा था। –

1

अगर मैं तुम्हें सही ढंग से समझ, आप केवल एक स्तंभ पर डुप्लिकेट बाहर करने के लिए सूचीबद्ध करना चाहते हैं, भीतर एक उप चयन

select u.* [whatever joined values] 
from users u 
inner join 
(select name from users group by name having count(*)=1) uniquenames 
on uniquenames.name = u.name 
2

आपका प्रश्न करने में शामिल होने के एक तरह से भ्रामक है; क्या आप प्रति उपयोगकर्ता केवल एक पंक्ति दिखाना चाहते हैं, या आप प्रति चित्र एक पंक्ति दिखाना चाहते हैं लेकिन U.NAME फ़ील्ड में दोहराने वाले मानों को दबाएं? मुझे लगता है कि आप दूसरा चाहते हैं; अगर पहले के लिए बहुत सारे जवाब नहीं हैं।

दोहराने वाले मान प्रदर्शित करना चाहे तर्क तर्क है, जिसे एसक्यूएल वास्तव में डिजाइन नहीं किया गया था। परिणाम पंक्ति-दर-पंक्ति को संसाधित करने के लिए आप एक लूप में कर्सर का उपयोग कर सकते हैं, लेकिन आप बहुत सारे प्रदर्शन खो देंगे। यदि आपके पास .NET भाषा या जावा जैसी "स्मार्ट" फ्रंटेंड भाषा है, तो जो भी निर्माण आपने इस डेटा को रखा है उसे यूआई में अंततः प्रदर्शित करने से पहले दोहराने वाले मूल्यों को दबाने के लिए सस्ती रूप से छेड़छाड़ की जा सकती है।

यदि आप माइक्रोसॉफ्ट एसक्यूएल सर्वर का उपयोग कर रहे हैं, और डेटा परत पर परिवर्तन किया जाना है, तो आप प्रारंभिक क्वेरी को पकड़ने के लिए एक सीटीई (संगणित तालिका अभिव्यक्ति) का उपयोग करने पर विचार कर सकते हैं, फिर प्रत्येक पंक्ति से मूल्यों का चयन करें सीटीई इस बात पर आधारित है कि पिछली पंक्ति में कॉलम समान डेटा रखते हैं या नहीं। यह कर्सर की तुलना में अधिक प्रदर्शनशील होगा, लेकिन यह किसी भी तरह से गन्दा हो जाएगा। निरीक्षण करें:

USING CTE (Row, Name, PicID) 
AS 
(
    SELECT ROW_NUMBER() OVER (ORDER BY U.NAME, P.PIC_ID), 
     U.NAME, P.PIC_ID 
    FROM USERS U 
     INNER JOIN POSTINGS P1 
      ON U.EMAIL_ID = P1.EMAIL_ID 
     INNER JOIN PICTURES P 
      ON P1.PIC_ID = P.PIC_ID 
    WHERE P.CAPTION LIKE '%car%' 
    ORDER BY U.NAME, P.PIC_ID 
) 
SELECT 
    CASE WHEN current.Name == previous.Name THEN '' ELSE current.Name END, 
    current.PicID 
FROM CTE current 
LEFT OUTER JOIN CTE previous 
    ON current.Row = previous.Row + 1 
ORDER BY current.Row 

उपर्युक्त नमूना TSQL- विशिष्ट है; पीएल/एसक्यूएल जैसे किसी भी अन्य डीबीपीएल में काम करने की गारंटी नहीं है, लेकिन मुझे लगता है कि अधिकांश एंटरप्राइज़-स्तरीय एसक्यूएल इंजनों में कुछ समान है।

संबंधित मुद्दे