2013-02-14 13 views
5

से अन्य पंक्तियां प्राप्त करें मेरे पास एक समग्र फ़ंक्शन है जो समूह (ए) द्वारा करता है। यह कॉलम के सेट (कॉल बी) से अधिकतम मान का चयन करता है, लेकिन मैं एक ही पंक्ति (कॉल सी) में कॉलम से एक और मान वापस करना चाहता हूं। लेकिन अगर यह 3 पंक्तियों को समूहित करता है तो यह कॉलम सी से पहला मान चुनता है जिसमें अधिकतम (MAX (col B)) कॉलम नहीं होता है।एसक्यूएल कुल फंक्शन

A B C 
1  75 jkl 
1 100 abc 
1 125 dae 
2 200 def 
3 300 ghi 

"SELECT A, MAX(B), C FROM myTable where B > 50 GROUP BY A" 

returns (first row) A => 1, B => 125, C => jkl 

I want it to return 

A => 1, B => 125, C => dae 

उत्तर

9

आप एक सबक्वेरी कि प्रत्येक A द्वारा max(b) मिल जाएगा और उसके बाद शेष कॉलम कि सबक्वेरी के मान से मेल लौटने के लिए अपनी मेज पर वापस कि मूल्य में शामिल होने का उपयोग करना चाहते जाएगा:

select * 
from mytable t1 
inner join 
(
    select A, max(b) B 
    from mytable 
    where b >50 
    group by a 
) t2 
    on t1.a = t2.a 
    and t1.b = t2.b 
where t1.b >50 

देखें SQL Fiddle with Demo

+0

के लिए केवल MAX (बी) एकत्रित करने के बाद एसक्यूएल प्रश्नों को तेजी से घोंसला कर रहे हैं और फिर प्रत्येक MAX (बी) के लिए एक क्वेरी चला रहे हैं? –

+0

@TheHawk मुझे समझ में नहीं आता कि आप क्या पूछ रहे हैं, क्या आप स्पष्टीकरण दे सकते हैं? – Taryn

+0

यदि मैं खुद से नेस्टेड क्वेरी चलाता हूं तो मुझे परिणाम अधिकतम सभी (बी) के साथ सेट मिलता है। मैं अधिकतम (बी) के परिणाम सेट के माध्यम से लूप करता हूं और प्रत्येक अधिकतम (बी) के लिए एक चयन चलाता हूं। असल में एक नेस्टेड क्वेरी के समान ही बात है लेकिन इसे मैन्युअल रूप से करने का तरीका –

5

जब से तुम आरडीबीएमएस प्रयोग कर रहे हैं उल्लेख नहीं किया है, इस क्वेरी जो लगभग सभी आरडीबीएमएस पर काम करता है का उपयोग

SELECT a.* 
FROM tableName a 
     INNER JOIN 
     (
      SELECT A, MAX(b) max_B 
      FROM tableName 
      WHERE b > 50 
      GROUP BY A 
     ) b ON a.A = b.A AND 
      a.B = b.max_B 

लेकिन यदि आपका आरडीबीएमएस समर्थन विंडो फ़ंक्शन करता है, तो आप 0 का उपयोग कर सकते हैं

SELECT A, B, C 
FROM  
     (
      SELECT A, B, C, 
        DENSE_RANK() OVER (PARTITION A ORDER BY B DESC) rn 
      FROM tableName 
      WHERE b > 50 
      GROUP BY  
     ) a 
WHERE rn = 1 

+0

केवल MAX (बी) एकत्रित करने और MAX (बी) के प्रत्येक के लिए एक क्वेरी चलाने के बजाय एसक्यूएल प्रश्नों को तेजी से घोंसला कर रहे हैं? –

+0

यदि आप कॉलम ए और बी –

+0

पर कंपाउंड इंडेक्स जोड़ देंगे तो यह अधिक कुशल होगा DENSE_RANK नोट के लिए धन्यवाद। एक ही सवाल था लेकिन SQL सर्वर – Scott

3

यह एक बहुत ही आम समस्या है - "मुझे मेरे न्यूनतम()/अधिकतम() कुल मानदंडों से मेल खाने वाली पंक्तियों पर अन्य कॉलम दिखाएं।" बड़ी टेबल पर, सबक्वायरी रणनीतियों को बहुत धीमा हो सकता है, और रैंकिंग फ़ंक्शन कभी-कभी बेहतर नहीं होते हैं।

SELECT A, cast(left(val, 8) as int) AS B, substring(val, 9, 999) AS C 
FROM (SELECT A, max(str(B, 8) + C) AS val FROM myTable GROUP BY A) t 

आप जो भी चाहें जोड़ सकते हैं:

यदि आप इसे चारों ओर अपने सिर प्राप्त करने के लिए तैयार हैं, यह इस संभाल करने के लिए सबसे शक्तिशाली तरीका है (हालांकि फिर से, नहीं सबसे पठनीय) अब तक आप max आईएनजी के लिए, फिर इसे बाहरी क्वेरी में निकालें। देखा।

ध्यान दें कि यह ब्लूफेट और जेडब्लू द्वारा पोस्ट किए गए समाधानों के मुकाबले अलग-अलग परिणाम लौटाएगा, यदि प्रति समूह अधिकतम मिलान करने वाले अधिकतम मूल्य हैं, तो यह विधि विजेता (सबसे बड़ी सी) लेगी जबकि अन्य कई रिकॉर्ड वापस करेंगे । इसलिए, यदि तीसरा बी मान 125 के बजाय 100 था, तो यह 1, 100, डीए लौटाएगा जबकि अन्य समाधान 1, 100, abd और 1, 100, dae दोनों लौटाएंगे।

+0

यह बहुत अच्छा लग रहा है। हालांकि, जब MAX फ़ंक्शन चलता है तो सी को ध्यान में रखा जाता है। यह सी पर भी MAX है, लेकिन मेरा मानना ​​है कि वह संबंधित सी मान को "किसी विशेष ए के लिए अधिकतम बी" चाहता है। इसका मतलब है टाई में, क्वेरी में दो परिणाम होना चाहिए। ऐसा इसलिए है क्योंकि हमें लगता है कि सी को खाते में मूल्य नहीं लेना चाहिए। – VISQL

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