2013-08-15 16 views
27

में डिस्टिंट का चयन करें मैं स्लिम 1 का उपयोग कर रहा हूं, और मुझे किसी संबंधित तालिका में किसी शर्त से मेल खाने वाली सभी इकाइयों को देखने के लिए एक क्वेरी में फ़िल्टर लागू करने में सक्षम होना चाहिए।स्कैला स्लिक

यह उदाहरण स्लिक प्रलेखन का उपयोग कर पता चलता है कि मैं क्या करने के लिए कोशिश कर रहा हूँ (यह एक काल्पनिक उदाहरण है कि मेरी स्थिति के करीब है है)।

यहां, मैं सभी कॉफ़ी चाहता हूं जो पश्चिम तट पर आपूर्तिकर्ताओं द्वारा प्रदान किए जाते हैं। मैं चाहता हूँ कॉफी केवल, मैं सिर्फ आपूर्तिकर्ता है, वहाँ नेविगेट फ़िल्टर लागू करने में दिलचस्पी है:

val westCoast = Seq("CA", "OR", "WA") 
val implicitInnerJoin = for { 
    c <- Coffees 
    s <- Suppliers if c.supID === s.id && s.state inSet westCoast 
} yield c 

यह ठीक काम करता है, लेकिन यह कॉफी नकल होगा अगर वहाँ आपूर्तिकर्ता तालिका में एक से अधिक मैच है।

स्पष्ट समाधान एक एसक्यूएल डिस्टिंट करने के लिए सामान्य एसक्यूएल में है; हालांकि, मुझे यहां ऐसा करने का कोई तरीका नहीं मिल रहा है। परिणाम के बाद पहले से ही लौटा दिया जाता है

query.list.distinct 

;:

आप सिद्धांत में एक कर सकता है हालांकि, मैंने पेजिंग समर्थन भी लागू किया है, इसलिए डेटाबेस से वापस आने के बाद आप परिणामों को संसाधित नहीं करना चाहेंगे।

query.drop(offset).take(limit).list 

तो, संक्षेप में, मैं एक तरह से मेरी क्वेरी कि बाहर चला जाता है में अलग चयन निर्दिष्ट करने की आवश्यकता : यहाँ पेजिंग समर्थन है।

किसी के पास कोई विचार है?

उत्तर

17

देखें एक काम के रूप में चारों ओर आप GroupBy उपयोग करने का प्रयास कर सकते हैं:

query.groupBy(x=>x).map(_._1) 

यह अलग रूप में एक ही अर्थ विज्ञान होना चाहिए, लेकिन मैं प्रदर्शन के बारे में यकीन नहीं है।

+0

अरे, यह एक काम पर विलय कर दिया गया था! मुझे बिल्कुल यकीन नहीं है कि क्यों, मैंने गहरे गोताखोरी का अधिक काम नहीं किया है, लेकिन मुझे एक त्वरित सुधार की जरूरत है। – noplay

+0

किसी कारण से, यह मुझे 'XxxRow' इकाई के बजाय' scala.TupleN' देता है, जिसमें 'क्लासकास्टएक्सप्शन' फेंक दिया जाता है। –

+0

ऐसा लगता है कि यह कारण है: https://github.com/slick/slick/pull/735 –

13

स्लिम 3.1.0 के साथ आप distinct और distinctOn फ़ंक्शंस (Slick 3.1.0 release notes) का उपयोग कर सकते हैं।

val westCoast = Seq("CA", "OR", "WA") 
val implicitInnerJoin = for { 
    c <- Coffees 
    s <- Suppliers if c.supID === s.id && s.state inSet westCoast 
} yield c 

db.run(implicitInnerJoin.distinctOn(_.name).result) 
+1

FWIW, फिलहाल [अलग-अलग के साथ एक बग] (https://github.com/slick/slick/issues/1712) प्रतीत होता है। – Nick

2

अलग के लिए एकाधिक स्तंभों पर coffee.name और coffee.price: उदाहरण के लिए:

val westCoast = Seq("CA", "OR", "WA") 
val implicitInnerJoin = for { 
    c <- Coffees 
    s <- Suppliers if c.supID === s.id && s.state inSet westCoast 
} yield c 

db.run(implicitInnerJoin.map(f => (f.name, f.price, f.state)).distinctOn(p => (p._1, p._2)).result) 
+0

इसे आपके द्वारा वर्णित ** विशिष्ट आदेश ** होना चाहिए - यानी 'नक्शा (ए => (ए.आईडी, ए.नाम))। DisctinctOn (a => (a._1, a._2)) ' या किसी को 'स्लिम कुंजी नहीं मिली: s2' रनटाइम अपवाद। 'DifferenOn (a => (a.id, a.name)) करना' काम नहीं करेगा –

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