MySQL "के साथ" खंड


98

मैं "विथ" क्लॉज के साथ एक दृश्य बनाने के लिए MySQL का उपयोग करने की कोशिश कर रहा हूं

WITH authorRating(aname, rating) AS
   SELECT aname, AVG(quantity)
   FROM book
   GROUP BY aname

लेकिन ऐसा नहीं लगता कि MySQL इसको सपोर्ट करता है।

मैंने सोचा कि यह बहुत मानक था और मुझे यकीन है कि ओरेकल इस का समर्थन करता है। वहाँ वैसे भी MySQL के लिए "के साथ" का उपयोग करने के लिए मजबूर करने के लिए है? मैंने इसे MyISAM और innoDB इंजन के साथ आज़माया है। ये दोनों काम नहीं करते हैं।

जवाबों:


109

अपडेट: MySQL 8.0 को अंत में पुनरावर्ती CTE सहित सामान्य तालिका अभिव्यक्तियों की सुविधा मिल रही है।

यहाँ यह घोषणा करने वाला एक ब्लॉग है: http://mysqlserverteam.com/mysql-8-0-labs-recursive-common-table-expressions-in-mysql-ctes/

नीचे मेरा पूर्व उत्तर है, जो मैंने मूल रूप से 2008 में लिखा था।


MySQL 5.x WITHSQL-99 में परिभाषित सिंटैक्स का उपयोग करके प्रश्नों का समर्थन नहीं करता है , जिसे कॉमन टेबल एक्सप्रेशंस भी कहा जाता है

यह जनवरी 2006 के बाद से MySQL के लिए एक सुविधा अनुरोध रहा है: http://bugs.mysql.com/bug.php?id=1664

अन्य RDBMS उत्पाद जो सामान्य तालिका अभिव्यक्तियों का समर्थन करते हैं:


1
SQLite 2014-02-03 को जारी संस्करण 3.8.3 के रूप में क्लॉज़ विथ द क्लॉज़ का समर्थन करता है ।
Martijn

मैंने सूची में H2 और फायरबर्ड को जोड़ा।
a_horse_with_no_name

2
@BillKarwin: मेरा मानना ​​है कि MySQL कभी भी किसी भी आधुनिक DBMS सुविधा (चेक की कमी, विंडो फ़ंक्शन, इंडेक्स ऑन एक्सप्रेशंस, आंशिक इंडेक्स, आस्थगित बाधाओं ...) को लागू करेगा।
a_horse_with_no_name

2
@a_horse_with_no_name, वे स्केलेबिलिटी पर बहुत अधिक प्राथमिकता देते हैं। आधुनिक हार्डवेयर का लाभ उठाने के लिए, उन्होंने अपने इंटर्न को अधिक स्केलेबल बनाने पर लंबे समय तक ध्यान केंद्रित किया है। लेकिन मुझे लगता है कि उन्होंने SQL सुविधाओं की उपेक्षा की है।
बिल कार्विन

1
@BlakeMcBride, आप गलत हैं, आपकी टिप्पणी FUD है और वास्तव में इसका कोई आधार नहीं है। ओरेकल अन्य डेटाबेस उत्पादों का भी मालिक है जो ओरेकल डीबी अच्छा नहीं करता है। उदाहरण: टाइम्सटेन, बर्कलेबीडी। उन्होंने अपने बाजार का विस्तार करने के लिए उन डेटाबेसों का अधिग्रहण किया। वेब एप्लिकेशन मार्केट में MySQL प्रमुख है, और Oracle DB नहीं है, इसलिए उन्होंने MySQL का अधिग्रहण किया। यह Oracle के लिए MySQL हैमस्ट्रिंग के लिए कोई मतलब नहीं है। मैंने अप्रैल में सम्मेलन में ओरेकल MySQL डेवलपर्स से बात की, और वे वास्तव में MySQL के लिए लागू करने पर काम कर रहे हैं।
बिल करविन

17

आप इस तरह somethinkg में रुचि हो सकती है:

select * from (
    select * from table
) as Subquery

क्या आप सबक्वेरी को समझा सकते हैं? मैं कुछ से * (से (चयन करें * तालिका 1 से) का चयन कर सकते हैं) सभी (तालिका 2 से चयन)) समूह द्वारा कुछ?

1
@ कैथी हाय, Subqueryवह नाम है जिसका इस्तेमाल मैंने व्युत्पन्न तालिका के लिए किया था। जब आप उपयोग from ( ... )करते हैं तो आप एक अस्थायी तालिका (एक व्युत्पन्न तालिका) जैसा कुछ बनाते हैं और इसके लिए एक नाम की आवश्यकता होती है। इसलिए मैंने इस्तेमाल किया as Subquery। आपके प्रश्न का उत्तर देते हुए, हां, आप कर सकते हैं, लेकिन आपको बाहरी व्युत्पन्न तालिका में (बस पहले Group By) नाम डालना होगा । उम्मीद है कि मदद की।
मोस्ट मोस्टैको

@MostyMostacho हैलो, कृपया मुझे एक छोटे से यहाँ खिला सकते हैं? मैं इसे MySQL में बदलने के लिए संघर्ष कर रहा हूँ। क्या आप इस पर एक नज़र डाल सकते हैं? लिंक या मेरे सवाल का जवाब शायद यहाँ? लिंक
प्रणव

13

आपको सिंटैक्स सही मिला है:

WITH AuthorRating(AuthorName, AuthorRating) AS
   SELECT aname         AS AuthorName,
          AVG(quantity) AS AuthorRating
   FROM Book
   GROUP By Book.aname

हालाँकि, जैसा कि दूसरों ने उल्लेख किया है, MySQL इस कमांड का समर्थन नहीं करता है। SQL में जोड़ा गया था: 1999; SQL मानक का नवीनतम संस्करण SQL: 2008 है। आप उन डेटाबेस के बारे में कुछ और जानकारी पा सकते हैं जो एसक्यूएल का समर्थन करते हैं: 1999 विकिपीडिया पर विभिन्न विशेषताएं ।

MySQL पारंपरिक रूप से SQL मानक के समर्थन में थोड़ा पिछड़ गया है, जबकि ओरेकल, SQL सर्वर (हाल ही में), और DB2 जैसे व्यावसायिक डेटाबेस ने उन्हें थोड़ा और करीब से देखा है। PostgreSQL आमतौर पर बहुत मानकों के अनुरूप है।

आप MySQL के रोडमैप को देखना चाहते हैं; जब इस सुविधा का समर्थन किया जा सकता है तो मुझे पूरा यकीन नहीं है, लेकिन यह पठनीय रोल-अप क्वेरी बनाने के लिए बहुत अच्छा है।


9

Oracle समर्थन करता है।

यह इस तरह दिखेगा।

WITH emps as (SELECT * FROM Employees)
SELECT * FROM emps WHERE ID < 20
UNION ALL
SELECT * FROM emps where Sex = 'F'

@ysth को Google के लिए कठिन है क्योंकि यह आम तौर पर खोजों से बाहर रखा गया एक सामान्य शब्द है।

आप को देखने के लिए चाहते हैं का चयन करें डॉक्स को देखने के लिए कैसे सबक्वेरी फैक्टरिंग काम करता है।

मुझे पता है कि यह ओपी का जवाब नहीं देता है, लेकिन मैं किसी भी भ्रम को साफ कर सकता हूं कि शुरुआत हो सकती है।


वैसे भी मेरा भ्रम दूर नहीं किया। क्या आप कह रहे हैं कि एक खंड के साथ नहीं है, लेकिन एक बयान के साथ है?
ysth

1
ओह समझा। यह चयन का एक खंड है जो चयन से पहले होता है। क्या इसे क्रिएट व्यू में भी इस्तेमाल किया जा सकता है? यह सबसेक्ट में शामिल होने से कैसे अलग है? मुझे ऐसे उदाहरण ऑनलाइन नहीं दिखते हैं, जहां के नाम के बाद पैरामीटर हैं - वे कैसे काम करते हैं?
ysth

1
यह बहुत अलग है। ध्यान दें कि एक ही उप-वर्ग का उपयोग दो बार परिभाषित किए बिना किया जाता है। सुनिश्चित करें कि आप वहां उसी क्वेरी को कॉपी / पेस्ट कर सकते हैं लेकिन यह एक सरल उदाहरण है। कल्पना कीजिए कि अगर एक खंड के लिए एक पृष्ठ पर चला गया और मुख्य क्वेरी में 4 बार उपयोग किया गया था। आप इसकी सराहना करेंगे।

मैं डॉक्स से जुड़ा हुआ हूं, जिसे सिंटैक्स की व्याख्या करनी चाहिए। जहाँ तक एक दृश्य में है। ज़रूर वहाँ काम करता है।

3

@Mosty Mostacho के उत्तर पर निर्माण, यहां बताया गया है कि आप किस तरह MySQL में समतुल्य कुछ कर सकते हैं, यह निर्धारित करने के एक विशिष्ट मामले के लिए कि किसी तालिका में क्या प्रविष्टियाँ मौजूद नहीं हैं, और किसी अन्य डेटाबेस में नहीं हैं।

select col1 from (
   select 'value1' as col1 union
   select 'value2' as col1 union
   select 'value3' as col1
) as subquery
left join mytable as mytable.mycol = col1
where mytable.mycol is null
order by col1

आप मानों की सूची को उद्धृत चुनिंदा संघ खंड में परिवर्तित करने के लिए मैक्रो क्षमताओं के साथ एक पाठ संपादक का उपयोग करना चाह सकते हैं।




0

क्या आपने कभी अस्थायी तालिका की कोशिश की है? इससे मेरा अभिसरण हल हो गया:

create temporary table abc (
column1 varchar(255)
column2 decimal
);
insert into abc
select ...
or otherwise
insert into abc
values ('text', 5.5), ('text2', 0815.8);

फिर आप इस सत्र में हर तालिका में इस तालिका का उपयोग कर सकते हैं:

select * from abc inner join users on ...;

1
मुझे ध्यान देना होगा: stackoverflow.com/questions/343402/… आप दो बार टेबल नहीं खोल सकते :-(
क्लॉस

तालिकाओं में छोटे डेटा सेट के लिए मेरा सोल्लुशन: एबीसी की तरह टेबल एबीसी 2 बनाएं; abc2 में डालें * abc से चुनें;
क्लॉस
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.