Database
 sql >> डेटाबेस >  >> RDS >> Database

टेबल एक्सप्रेशन के फंडामेंटल, भाग 2 - व्युत्पन्न टेबल, तार्किक विचार

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

यदि आप कुछ समय के लिए टी-एसक्यूएल के साथ काम कर रहे हैं, तो आप शायद कुछ ऐसे मामलों में फंस गए हैं जहां आपको या तो टेबल एक्सप्रेशन का उपयोग करना पड़ा था, या वैकल्पिक समाधानों की तुलना में यह किसी भी तरह से अधिक सुविधाजनक था जो उनका उपयोग नहीं करते थे। उपयोग के मामलों के लिए यहां कुछ उदाहरण दिए गए हैं जो दिमाग में आते हैं:

  • जटिल कार्यों को चरणों में विभाजित करके एक मॉड्यूलर समाधान बनाएं, प्रत्येक को एक अलग तालिका अभिव्यक्ति द्वारा दर्शाया गया है।
  • यदि आप इस उद्देश्य के लिए विंडो फ़ंक्शन का उपयोग नहीं करने का निर्णय लेते हैं, तो समूहबद्ध प्रश्नों और विवरण के परिणामों को मिलाना।
  • तार्किक क्वेरी संसाधन निम्नलिखित क्रम में क्वेरी क्लॉज को हैंडल करता है:FROM>WHERE>GROUP BY>HAVING>SELECT>ORDER BY। नतीजतन, नेस्टिंग के समान स्तर में, कॉलम उपनाम जिन्हें आप SELECT क्लॉज में परिभाषित करते हैं, केवल ORDER BY क्लॉज के लिए उपलब्ध होते हैं। वे शेष क्वेरी क्लॉज़ के लिए उपलब्ध नहीं हैं। तालिका अभिव्यक्तियों के साथ आप बाहरी क्वेरी के किसी भी खंड में आंतरिक क्वेरी में परिभाषित उपनामों का पुन:उपयोग कर सकते हैं, और इस तरह लंबी/जटिल अभिव्यक्तियों की पुनरावृत्ति से बच सकते हैं।
  • विंडो फ़ंक्शन केवल क्वेरी के SELECT और ORDER BY क्लॉज़ में दिखाई दे सकते हैं। टेबल एक्सप्रेशन के साथ, आप विंडो फ़ंक्शन के आधार पर एक एक्सप्रेशन के लिए उपनाम असाइन कर सकते हैं, और फिर टेबल एक्सप्रेशन के विरुद्ध क्वेरी में उस उपनाम का उपयोग कर सकते हैं।
  • एक PIVOT ऑपरेटर में तीन तत्व शामिल होते हैं:समूहीकरण, प्रसार और एकत्रीकरण। यह ऑपरेटर समूहीकरण तत्व को परोक्ष रूप से उन्मूलन द्वारा पहचानता है। एक टेबल एक्सप्रेशन का उपयोग करके, आप वास्तव में शामिल किए जाने वाले तीन तत्वों को प्रोजेक्ट कर सकते हैं, और बाहरी क्वेरी को PIVOT ऑपरेटर की इनपुट टेबल के रूप में टेबल एक्सप्रेशन का उपयोग करना चाहिए, इस प्रकार यह नियंत्रित करना कि कौन सा तत्व ग्रुपिंग एलिमेंट है।
  • TOP वाले संशोधन ORDER BY खंड का समर्थन नहीं करते हैं। आप टॉप या ऑफ़सेट-फ़ेच फ़िल्टर और ORDER BY क्लॉज़ के साथ SELECT क्वेरी के आधार पर टेबल एक्सप्रेशन को परिभाषित करके परोक्ष रूप से चुनी गई पंक्तियों को नियंत्रित कर सकते हैं और टेबल एक्सप्रेशन के खिलाफ संशोधन लागू कर सकते हैं।

यह एक संपूर्ण सूची होने से बहुत दूर है। मैं इस श्रृंखला में उपरोक्त उपयोग के कुछ मामलों और अन्य को प्रदर्शित करूंगा। मैं यहां कुछ उपयोग के मामलों का उल्लेख करना चाहता हूं ताकि यह स्पष्ट किया जा सके कि हमारे टी-एसक्यूएल कोड में टेबल एक्सप्रेशन कितने महत्वपूर्ण हैं, और उनके मूल सिद्धांतों को अच्छी तरह से समझने में निवेश करना क्यों उचित है।

इस महीने के लेख में मैं विशेष रूप से व्युत्पन्न तालिकाओं के तार्किक उपचार पर ध्यान केंद्रित करता हूं।

अपने उदाहरणों में मैं TSQLV5 नामक एक नमूना डेटाबेस का उपयोग करूँगा। आप उस स्क्रिप्ट को ढूंढ सकते हैं जो इसे यहां बनाता है और पॉप्युलेट करता है, और इसका ईआर आरेख यहां ।

व्युत्पन्न टेबल

व्युत्पन्न तालिका शब्द का प्रयोग SQL और T-SQL में एक से अधिक अर्थों के साथ किया जाता है। इसलिए सबसे पहले मैं यह स्पष्ट कर देना चाहता हूं कि मैं इस लेख में किसका जिक्र कर रहा हूं। मैं एक विशिष्ट भाषा निर्माण की बात कर रहा हूं जिसे आप आमतौर पर परिभाषित करते हैं, लेकिन न केवल बाहरी क्वेरी के FROM खंड में। मैं इस निर्माण के लिए शीघ्र ही सिंटैक्स प्रदान करूँगा।

एसक्यूएल में व्युत्पन्न तालिका शब्द का अधिक सामान्य उपयोग संबंधपरक सिद्धांत से व्युत्पन्न संबंध के समकक्ष है। एक व्युत्पन्न संबंध एक परिणाम संबंध है जो एक या एक से अधिक इनपुट बेस संबंधों से प्राप्त होता है, रिलेशनल ऑपरेटर्स को रिलेशनल बीजगणित जैसे प्रोजेक्शन, इंटरसेक्शन और अन्य को उन बेस रिलेशन से लागू करके। इसी तरह, सामान्य अर्थों में, SQL में एक व्युत्पन्न तालिका एक परिणाम तालिका है जो उन इनपुट बेस टेबलों के विरुद्ध भावों का मूल्यांकन करके एक या अधिक आधार तालिकाओं से प्राप्त होती है।

एक तरफ के रूप में, मैंने जाँच की कि SQL मानक एक आधार तालिका को कैसे परिभाषित करता है और मुझे तुरंत खेद हुआ कि मैंने परेशान किया।

4.15.2 बेस टेबल

आधार तालिका या तो स्थायी आधार तालिका या अस्थायी तालिका होती है।

एक स्थायी आधार तालिका या तो एक नियमित स्थायी आधार तालिका या एक सिस्टम-संस्करण तालिका है।

एक नियमित आधार तालिका या तो एक नियमित स्थायी आधार तालिका या एक अस्थायी तालिका होती है।"

बिना किसी और टिप्पणी के यहां जोड़ा गया...

T-SQL में, आप CREATE TABLE स्टेटमेंट के साथ एक बेस टेबल बना सकते हैं, लेकिन अन्य विकल्प भी हैं, जैसे, SELECT INTO और DECLARE @T AS TABLE।

यहाँ सामान्य अर्थों में व्युत्पन्न तालिकाओं के लिए मानक की परिभाषा दी गई है:

4.15.3 व्युत्पन्न तालिकाएं

एक व्युत्पन्न तालिका एक अभिव्यक्ति के मूल्यांकन द्वारा एक या एक से अधिक अन्य तालिकाओं से प्रत्यक्ष या परोक्ष रूप से प्राप्त एक तालिका है, जैसे <शामिल तालिका>, <डेटा परिवर्तन डेल्टा तालिका>, <क्वेरी अभिव्यक्ति>, या <तालिका अभिव्यक्ति>। एक <क्वेरी एक्सप्रेशन> में एक वैकल्पिक <ऑर्डर बाय क्लॉज> हो सकता है। <क्वेरी एक्सप्रेशन> द्वारा निर्दिष्ट तालिका की पंक्तियों के क्रम की गारंटी केवल <क्वेरी एक्सप्रेशन> के लिए है जिसमें तुरंत <ऑर्डर बाय क्लॉज> शामिल है।"

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

सेल्स से कंपनी का नाम, कंपनी का नाम चुनें। ग्राहक जहां देश =एन'यूएसए'

इसके विपरीत, निम्न व्यंजक एक व्युत्पन्न तालिका का प्रतिनिधित्व करता है, लेकिन नहीं एक मान्य स्टैंड-अलोन टेबल एक्सप्रेशन:

T1 इनर T1.keycol =T2.keycol पर T2 में शामिल हों

टी-एसक्यूएल कई टेबल ऑपरेटरों का समर्थन करता है जो एक व्युत्पन्न तालिका उत्पन्न करते हैं, लेकिन स्टैंड-अलोन एक्सप्रेशन के रूप में समर्थित नहीं हैं। वे हैं:जॉइन, पिवोट, अनपिवोट और एप्लाई। आपको उनके भीतर काम करने के लिए एक क्लॉज की आवश्यकता होती है (आमतौर पर FROM, लेकिन MERGE स्टेटमेंट का USING क्लॉज भी), और एक होस्ट क्वेरी।

यहाँ से, मैं एक अधिक विशिष्ट भाषा निर्माण का वर्णन करने के लिए व्युत्पन्न तालिका शब्द का उपयोग करूँगा, न कि ऊपर वर्णित सामान्य अर्थों में।

सिंटैक्स

एक व्युत्पन्न तालिका को इसके FROM खंड में बाहरी चयन कथन के भाग के रूप में परिभाषित किया जा सकता है। इसे उनके FROM क्लॉज में DELETE और UPDATE स्टेटमेंट के हिस्से के रूप में और इसके USING क्लॉज में MERGE स्टेटमेंट के हिस्से के रूप में भी परिभाषित किया जा सकता है। इस आलेख में बाद में संशोधन कथनों में उपयोग किए जाने पर मैं सिंटैक्स पर अधिक विवरण प्रदान करूंगा।

व्युत्पन्न तालिका के विरुद्ध सरलीकृत चयन क्वेरी के लिए सिंटैक्स यहां दिया गया है:

चयन करें <सूची का चयन करें>
<मजबूत शैली ="फ़ॉन्ट-परिवार:मोंटसेराट! महत्वपूर्ण"> से (<तालिका अभिव्यक्ति>) [एएस] <तालिका का नाम> [ (<लक्ष्य कॉलम>)] ;

व्युत्पन्न तालिका परिभाषा प्रकट होती है जहां बाहरी क्वेरी के FROM क्लॉज में एक आधार तालिका सामान्य रूप से दिखाई दे सकती है। यह जॉइन, एप्लाई, पिवोट और यूएनपीवीओटी जैसे टेबल ऑपरेटर के लिए इनपुट हो सकता है। जब एक लागू ऑपरेटर के लिए सही इनपुट के रूप में उपयोग किया जाता है, तो व्युत्पन्न तालिका के <तालिका अभिव्यक्ति> भाग को बाहरी तालिका से कॉलम के साथ सहसंबंध रखने की अनुमति है (इस पर श्रृंखला में समर्पित भविष्य के लेख में अधिक)। अन्यथा, टेबल एक्सप्रेशन स्व-निहित होना चाहिए।

बाहरी कथन में सभी सामान्य क्वेरी तत्व हो सकते हैं। एक सेलेक्ट स्टेटमेंट केस में:WHERE, GROUP BY, HAVING, ORDER BY और जैसा कि उल्लेख किया गया है, FROM क्लॉज में टेबल ऑपरेटर।

संयुक्त राज्य अमेरिका के ग्राहकों का प्रतिनिधित्व करने वाली व्युत्पन्न तालिका के विरुद्ध एक साधारण क्वेरी के लिए यहां एक उदाहरण दिया गया है:

कस्टिड चुनें, कंपनी का नामFROM ( सेलेक्ट कस्टिड, कंपनी का नाम सेल्स से। ग्राहक जहां देश =N'USA') AS UC;

यह क्वेरी निम्न आउटपुट उत्पन्न करती है:

कस्टिड कंपनी का नाम ------------------ 32 ग्राहक YSIQX36 ग्राहक LVJSO43 ग्राहक UISOJ45 ग्राहक QXPPT48 ग्राहक DVFMB55 ग्राहक KZQZT65 ग्राहक NYUHS71 ग्राहक LCOUJ75 ग्राहक XOJYP77 ग्राहक LCYBZ78 ग्राहक NLTYP82 ग्राहक EYHKM89 ग्राहक YBQTI

व्युत्पन्न तालिका परिभाषा वाले एक बयान में पहचानने के लिए तीन मुख्य भाग हैं:

  1. टेबल एक्सप्रेशन (आंतरिक क्वेरी)
  2. व्युत्पन्न तालिका नाम, या अधिक सटीक रूप से, संबंधपरक सिद्धांत में जिसे श्रेणी चर माना जाता है
  3. बाहरी बयान

तालिका अभिव्यक्ति को एक तालिका का प्रतिनिधित्व करना चाहिए, और इस तरह, कुछ आवश्यकताओं को पूरा करना चाहिए जो एक सामान्य क्वेरी को संतुष्ट करने की आवश्यकता नहीं है। मैं जल्द ही "एक टेबल एक्सप्रेशन एक टेबल है" अनुभाग में विवरण प्रदान करूंगा।

लक्ष्य व्युत्पन्न तालिका नाम के लिए; टी-एसक्यूएल डेवलपर्स के बीच एक आम धारणा यह है कि यह केवल एक नाम या उपनाम है जिसे आप लक्ष्य तालिका में निर्दिष्ट करते हैं। इसी तरह, निम्नलिखित प्रश्न पर विचार करें:

कस्टिड चुनें, companynameFROM Sales.Customers AS CWHERE देश =N'USA';

यहां भी, आम धारणा यह है कि AS C, इस क्वेरी के प्रयोजनों के लिए तालिका Customers का नाम बदलने, या उपनाम करने का एक तरीका है, तार्किक क्वेरी प्रोसेसिंग चरण से शुरू होता है जहां नाम असाइन किया गया है और आगे। हालाँकि, संबंधपरक सिद्धांत के दृष्टिकोण से, C जो दर्शाता है उसका गहरा अर्थ है। सी वह है जिसे रेंज वेरिएबल के रूप में जाना जाता है। सी एक व्युत्पन्न संबंध चर है जो इनपुट संबंध चर ग्राहकों में टुपल्स पर होता है। उपरोक्त उदाहरण में, C ग्राहकों में टुपल्स के ऊपर है और विधेय देश =N'USA' का मूल्यांकन करता है। टुपल्स जिसके लिए विधेय सत्य का मूल्यांकन करता है, परिणाम संबंध C का हिस्सा बन जाता है।

टेबल एक्सप्रेशन एक टेबल है

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

  • टेबल एक्सप्रेशन के सभी कॉलम के नाम होने चाहिए
  • टेबल एक्सप्रेशन के सभी कॉलम नाम अद्वितीय होने चाहिए
  • टेबल एक्सप्रेशन की पंक्तियों का कोई क्रम नहीं है

आइए इन आवश्यकताओं को एक-एक करके तोड़ दें, रिलेशनल थ्योरी और SQL दोनों की प्रासंगिकता पर चर्चा करते हुए।

सभी स्तंभों के नाम होने चाहिए

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

मानव संसाधन से एम्पिड, प्रथम नाम, उपनाम, CONCAT_WS(N'/', देश, क्षेत्र, शहर) चुनें;

यह क्वेरी निम्न आउटपुट उत्पन्न करती है:

एम्पिड फर्स्टनाम लास्टनाम (कोई कॉलम नाम नहीं)---------------------------------------- ----1 सारा डेविस यूएसए/डब्ल्यूए/सिएटल2 डॉन फंक यूएसए/डब्ल्यूए/टैकोमा3 जूडी ल्यू यूएसए/डब्ल्यूए/किर्कलैंड4 येल पेलेड यूएसए/डब्ल्यूए/रेडमंड5 स्वेन मोर्टेंसन यूके/लंदन6 पॉल सुर्स यूके/लंदन7 रसेल किंग यूके/लंदन8 मारिया कैमरून यूएसए/डब्ल्यूए/सिएटल9 पेट्रीसिया डॉयल यूके/लंदन

CONCAT_WS फ़ंक्शन का उपयोग करके स्थान विशेषताओं के संयोजन के परिणामस्वरूप क्वेरी आउटपुट में एक अनाम कॉलम होता है। (वैसे, यह फ़ंक्शन SQL सर्वर 2017 में जोड़ा गया था, इसलिए यदि आप किसी पुराने संस्करण में कोड चला रहे हैं, तो बेझिझक इस गणना को अपनी पसंद की वैकल्पिक गणना के साथ बदलें।) इसलिए, यह क्वेरी नहीं है किसी रिश्ते की बात नहीं करने के लिए एक टेबल लौटाएं। इसलिए, इस तरह की क्वेरी का उपयोग टेबल एक्सप्रेशन/व्युत्पन्न तालिका परिभाषा के आंतरिक क्वेरी भाग के रूप में करना मान्य नहीं है।

इसे आज़माएं:

चुनें *FROM (सेलेक्ट एम्पिड, फर्स्टनाम, लास्टनाम, CONCAT_WS(N'/', देश, क्षेत्र, शहर) HR से।कर्मचारी) AS D;

आपको निम्न त्रुटि मिलती है:

Msg 8155, Level 16, State 2, Line 50
'D' के कॉलम 4 के लिए कोई कॉलम नाम निर्दिष्ट नहीं किया गया था।

एक तरफ, त्रुटि संदेश के बारे में कुछ दिलचस्प नोटिस करें? यह कॉलम 4 के बारे में शिकायत करता है, एसक्यूएल में कॉलम और रिलेशनल थ्योरी में विशेषताओं के बीच अंतर को उजागर करता है।

समाधान, निश्चित रूप से, यह सुनिश्चित करने के लिए है कि आप स्पष्ट रूप से उन स्तंभों को नाम निर्दिष्ट करते हैं जो गणनाओं के परिणामस्वरूप होते हैं। टी-एसक्यूएल कुछ कॉलम नामकरण तकनीकों का समर्थन करता है। मैं उनमें से दो का उल्लेख करूंगा।

आप एक इनलाइन नामकरण तकनीक का उपयोग कर सकते हैं जहां आप गणना के बाद लक्ष्य कॉलम नाम और एक वैकल्पिक AS क्लॉज असाइन करते हैं, जैसा कि < expression > [ AS ] < column name > में है। , इस तरह:

चुनें empid, firstname, lastname, custlocationFROM ( सेलेक्ट empid, firstname, lastname, CONCAT_WS(N'/', देश, क्षेत्र, शहर) AS कस्टलोकेशन HR से HR.कर्मचारी ) AS D;

यह क्वेरी निम्न आउटपुट उत्पन्न करती है:

एम्पिड फर्स्टनाम लास्टनाम कस्टलोकेशन--------------------------------------------------------------- सारा डेविस यूएसए/डब्ल्यूए/सिएटल2 डॉन फंक यूएसए/डब्ल्यूए/टैकोमा3 जूडी ल्यू यूएसए/डब्ल्यूए/किर्कलैंड4 येल पेलेड यूएसए/डब्ल्यूए/रेडमंड5 स्वेन मोर्टेंसन यूके/लंदन6 पॉल सुर्स यूके/लंदन7 रसेल किंग यूके/लंदन8 मारिया कैमरून यूएसए/डब्ल्यूए/सिएटल9 पेट्रीसिया डॉयल यूके/लंदन

इस तकनीक का उपयोग करते हुए, कोड की समीक्षा करते समय यह बताना बहुत आसान है कि कौन सा लक्ष्य कॉलम नाम किस अभिव्यक्ति को सौंपा गया है। साथ ही, आपको केवल उन स्तंभों को नाम देना होगा जिनके नाम पहले से नहीं हैं।

आप एक अधिक बाहरी कॉलम नामकरण तकनीक का भी उपयोग कर सकते हैं जहां आप व्युत्पन्न तालिका नाम के ठीक बाद कोष्ठक में लक्ष्य कॉलम नाम निर्दिष्ट करते हैं, जैसे:

सेलेक्ट एम्पिड, फर्स्टनाम, लास्टनाम, कस्टलोकेशनफ्रॉम (सेलेक्ट एम्पिड, फर्स्टनाम, लास्टनाम, CONCAT_WS(N'/', देश, क्षेत्र, शहर) एचआर से। कर्मचारी) एएस डी (एम्पिड, फर्स्टनाम, लास्टनाम, कस्टलोकेशन);

हालांकि इस तकनीक के साथ, आपको सभी कॉलमों के नाम सूचीबद्ध करने होंगे—जिनमें पहले से नाम वाले कॉलम भी शामिल हैं। लक्ष्य कॉलम नामों का असाइनमेंट स्थिति द्वारा किया जाता है, बाएं से दाएं, यानी, पहला लक्ष्य कॉलम नाम आंतरिक क्वेरी की चयन सूची में पहली अभिव्यक्ति का प्रतिनिधित्व करता है; दूसरा लक्ष्य स्तंभ नाम दूसरी अभिव्यक्ति का प्रतिनिधित्व करता है; और इसी तरह।

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

बाहरी नामकरण सिंटैक्स के साथ बग की संभावना को एक उदाहरण के साथ सबसे अच्छी तरह समझाया गया है।

एचआर.कर्मचारी तालिका से कर्मचारियों के पूरे सेट के साथ पिछली क्वेरी के आउटपुट की जांच करें। फिर, निम्न क्वेरी पर विचार करें, और इसे चलाने से पहले, यह पता लगाने का प्रयास करें कि आप परिणाम में किन कर्मचारियों को देखने की उम्मीद करते हैं:

सेलेक्ट एम्पिड, फर्स्टनाम, लास्टनाम, कस्टलोकेशनफ्रॉम (सेलेक्ट एम्पिड, फर्स्टनाम, लास्टनाम, CONCAT_WS(N'/', देश, क्षेत्र, शहर) एचआर से। कर्मचारी जहां अंतिम नाम एन'डी%' पसंद करते हैं) एएस डी (एम्पिड, अंतिम नाम, प्रथम नाम, ग्राहक स्थान)जहां पहला नाम N'D%' पसंद है;

यदि आप उम्मीद करते हैं कि क्वेरी दिए गए नमूना डेटा के लिए एक खाली सेट लौटाएगी, क्योंकि वर्तमान में अंतिम नाम और D अक्षर से शुरू होने वाले पहले नाम के साथ कोई कर्मचारी नहीं है, तो आप कोड में बग को याद कर रहे हैं।

अब क्वेरी चलाएँ, और वास्तविक आउटपुट की जाँच करें:

एम्पिड फर्स्टनाम लास्टनाम कस्टलोकेशन--------------------------------------------------------------डेविस सारा यूएसए/डब्ल्यूए/सिएटल9 डॉयल पेट्रीसिया यूके/लंदन

क्या हुआ?

आंतरिक क्वेरी पहले नाम को दूसरे कॉलम के रूप में और अंतिम नाम को SELECT सूची में तीसरे कॉलम के रूप में निर्दिष्ट करती है। बाहरी क्वेरी में व्युत्पन्न तालिका के लक्ष्य स्तंभ नामों को निर्दिष्ट करने वाला कोड अंतिम नाम दूसरा और पहला नाम तीसरा निर्दिष्ट करता है। कोड नाम प्रथम नाम अंतिम नाम के रूप में और अंतिम नाम श्रेणी चर डी में प्रथम नाम के रूप में। प्रभावी रूप से, आप केवल उन कर्मचारियों को फ़िल्टर कर रहे हैं जिनका अंतिम नाम अक्षर डी से शुरू होता है। आप कर्मचारियों को अंतिम नाम और प्रथम नाम दोनों के साथ फ़िल्टर नहीं कर रहे हैं जो शुरू होता है पत्र डी के साथ।

इनलाइन अलियासिंग सिंटैक्स ऐसे बग के लिए प्रवण नहीं है। एक के लिए, आप आम तौर पर उस कॉलम को उपनाम नहीं देते हैं जिसमें पहले से ही एक नाम है जिससे आप खुश हैं। दूसरा, भले ही आप उस कॉलम के लिए एक अलग उपनाम निर्दिष्ट करना चाहते हैं जिसमें पहले से ही एक नाम है, यह बहुत संभावना नहीं है कि सिंटैक्स <कॉलम> एएस <उपनाम> के साथ आप गलत उपनाम निर्दिष्ट करेंगे। इसके बारे में सोचो; इस बात की कितनी संभावना है कि आप इस तरह लिखेंगे:

सेलेक्ट एम्पिड, फर्स्टनाम, लास्टनाम, कस्टलोकेशनफ्रॉम (सेलेक्ट एम्पिड एएस एम्पिड, फर्स्टनाम एएस लास्टनाम, लास्टनाम एएस फर्स्टनाम, CONCAT_WS(N'/', देश, क्षेत्र, शहर) एचआर से कस्टलोकेशन के रूप में। कर्मचारी जहां अंतिम नाम एन'डी की तरह है %' ) DWHERE फर्स्टनाम LIKE N'D%';

जाहिर है, बहुत संभावना नहीं है।

सभी कॉलम नाम अद्वितीय होने चाहिए

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

एक उदाहरण के रूप में निम्नलिखित स्टैंडअलोन क्वेरी पर विचार करें:

C.custid, O.custid, O.orderidFROM सेलेक्ट करें। C LEFT OUTER JOIN सेल्स के रूप में ग्राहक। C.custid =O.custid पर O के रूप में ऑर्डर;

यह क्वेरी डुप्लिकेट कॉलम नाम त्रुटि के साथ विफल नहीं होती है क्योंकि एक custid कॉलम को वास्तव में C.custid और दूसरे O.custid को वर्तमान क्वेरी के दायरे में नाम दिया गया है। यह क्वेरी निम्न आउटपुट उत्पन्न करती है:

कस्टिड कस्टिड ऑर्डरिड----------------------------------------------1 1 106431 1 106921 1 107021 1 108351 1 109521 1 110112 2 103082 2 106252 2 107592 2 10926...

हालाँकि, इस क्वेरी को CO नामक व्युत्पन्न तालिका की परिभाषा में तालिका अभिव्यक्ति के रूप में उपयोग करने का प्रयास करें, जैसे:

सेलेक्ट *से (सेलेक्ट सी.कस्टिड, ओ.कस्टिड, ओ.ऑर्डरिड फ्रॉम सेल्स.कस्टमर ए एस सी लेफ्ट आउटर जॉइन सेल्स। सी.कस्टिड =ओ.कस्टिड पर ओ के रूप में ऑर्डर) सीओ के रूप में;

जहां तक ​​​​बाहरी क्वेरी का संबंध है, आपके पास CO नामक एक श्रेणी चर है, और बाहरी क्वेरी में सभी स्तंभ नामों का दायरा वह श्रेणी चर है। किसी दिए गए श्रेणी चर में सभी स्तंभों के नाम (याद रखें, एक श्रेणी चर एक संबंध चर है) अद्वितीय होना चाहिए। इसलिए, आपको निम्न त्रुटि मिलती है:

Msg 8156, Level 16, State 1, Line 80
कॉलम 'कस्टिड' को 'CO' के लिए कई बार निर्दिष्ट किया गया था।

जहां तक ​​रेंज वेरिएबल CO का संबंध है, दो कस्टिड कॉलमों को अलग-अलग कॉलम नाम असाइन करना निश्चित रूप से ठीक है, जैसे:

सेलेक्ट *से (सेलेक्ट C.custid AS custcustid, O.Custid AS ordercustid, O.orderid from Sales. Customers as C LEFT OUTER JOIN Sales.C.custid =O.custid के रूप में O. CO. के रूप में ऑर्डर करें;

यह क्वेरी निम्न आउटपुट उत्पन्न करती है:

कस्टकस्टिड ऑर्डरकस्टिड ऑर्डर----------- ----------------------1 1 106431 1 106921 1 107021 1 108351 1 109521 1 110112 2 103082 2 106252 2 107592 2 10926...

यदि आप अच्छी प्रथाओं का पालन करते हैं, तो आप स्पष्ट रूप से सबसे बाहरी क्वेरी की चयन सूची में कॉलम नामों को सूचीबद्ध करते हैं। चूंकि इसमें केवल एक श्रेणी चर शामिल है, इसलिए आपको बाहरी स्तंभ संदर्भों के लिए दो-भाग के नाम का उपयोग करने की आवश्यकता नहीं है। यदि आप दो-भाग के नाम का उपयोग करना चाहते हैं, तो आप बाहरी श्रेणी चर नाम CO के साथ कॉलम नामों को उपसर्ग करते हैं, जैसे:

 चयन करें CO.custcustid, CO.ordercustid, CO.orderidFROM (C.custid as custcustid, O.custid AS ordercustid, O.orderid बिक्री से चुनें। C. LEFT OUTER के रूप में ग्राहक बिक्री में शामिल हों। C.custid पर O के रूप में आदेश =O.custid ) AS CO;

कोई आदेश नहीं

नामित टेबल एक्सप्रेशन और ऑर्डरिंग के बारे में मुझे बहुत कुछ कहना है - अपने आप में एक लेख के लिए पर्याप्त है - इसलिए मैं इस विषय पर एक भविष्य का लेख समर्पित करूंगा। फिर भी, मैं यहाँ इस विषय को संक्षेप में बताना चाहता हूँ क्योंकि यह बहुत महत्वपूर्ण है। याद रखें कि रिश्ते का शरीर टुपल्स का एक सेट है, और इसी तरह, टेबल का शरीर पंक्तियों का एक सेट है। एक सेट का कोई आदेश नहीं है। फिर भी, SQL सबसे बाहरी क्वेरी को ORDER BY क्लॉज की अनुमति देता है जो एक प्रस्तुति ऑर्डरिंग अर्थ प्रदान करता है, जैसा कि निम्न क्वेरी प्रदर्शित करती है:

सेलेक्ट ऑर्डरिड, वैलफ्रॉम सेल्स।ऑर्डरवैल्यूसऑर्डर बाय वैल डीईएससी;

हालाँकि, आपको जो समझने की आवश्यकता है, वह यह है कि यह क्वेरी परिणाम के रूप में एक संबंध नहीं लौटाती है। SQL के दृष्टिकोण से भी, क्वेरी परिणाम के रूप में एक तालिका नहीं लौटाती है, और इसलिए यह नहीं है एक तालिका अभिव्यक्ति माना जाता है। नतीजतन, व्युत्पन्न तालिका परिभाषा के तालिका अभिव्यक्ति भाग के रूप में ऐसी क्वेरी का उपयोग करना अमान्य है।

निम्नलिखित कोड चलाने का प्रयास करें:

सेलेक्ट ऑर्डरिड, वैलफ्रॉम (सेलेक्ट ऑर्डरिड, वैल फ्रॉम सेल्स। ऑर्डर वैल्यूज ऑर्डर बाय वैल डीईएससी) एएस डी;

आपको निम्न त्रुटि मिलती है:

Msg 1033, Level 15, State 1, Line 124
ORDER BY क्लॉज व्यूज, इनलाइन फंक्शन्स, डिराइव्ड टेबल्स, सबक्वेरी और कॉमन टेबल एक्सप्रेशन में अमान्य है, जब तक कि TOP, OFFSET या FOR XML भी निर्दिष्ट न हो।

मैं जब तक . को संबोधित करूंगा शीघ्र ही त्रुटि संदेश का हिस्सा।

यदि आप चाहते हैं कि सबसे बाहरी क्वेरी एक आदेशित परिणाम लौटाए, तो आपको सबसे बाहरी क्वेरी में ORDER BY क्लॉज निर्दिष्ट करने की आवश्यकता है, जैसे:

सेलेक्ट ऑर्डरिड, वैलफ्रॉम (सेलेक्ट ऑर्डरिड, वैल फ्रॉम सेल्स.ऑर्डरवैल्यूज) वैल डीईएससी द्वारा ऑर्डर के रूप में;

जहां तक ​​जब तक . का संबंध है त्रुटि संदेश का हिस्सा; T-SQL मालिकाना TOP फ़िल्टर के साथ-साथ मानक OFFSET-FETCH फ़िल्टर का समर्थन करता है। दोनों फ़िल्टर एक ही क्वेरी स्कोप में ORDER BY क्लॉज पर निर्भर करते हैं ताकि उनके लिए यह निर्धारित किया जा सके कि कौन सी शीर्ष पंक्तियों को फ़िल्टर करना है। यह दुर्भाग्य से इन सुविधाओं के डिजाइन में एक जाल का परिणाम है, जो फ़िल्टर ऑर्डरिंग से प्रेजेंटेशन ऑर्डरिंग को अलग नहीं करता है। जैसा कि हो सकता है, Microsoft दोनों अपने TOP फ़िल्टर के साथ, और इसके OFFSET-FETCH फ़िल्टर के साथ मानक, आंतरिक क्वेरी में ORDER BY खंड निर्दिष्ट करने की अनुमति देते हैं, जब तक कि यह क्रमशः TOP या OFFSET-FETCH फ़िल्टर भी निर्दिष्ट करता है। इसलिए, यह क्वेरी मान्य है, उदाहरण के लिए:

सेलेक्ट ऑर्डरिड, वैलफ्रॉम (सेलेक्ट टॉप (3) ऑर्डरिड, वैल फ्रॉम सेल्स। ऑर्डर वैल्यू ऑर्डर बाय वैल डीईएससी) एएस डी;

जब मैंने इस क्वेरी को अपने सिस्टम पर चलाया, तो इसने निम्न आउटपुट उत्पन्न किया:

ऑर्डरिड वैल----------------10865 16387.5010981 15810.0011030 12615.05

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

"<क्वेरी एक्सप्रेशन> द्वारा निर्दिष्ट तालिका की पंक्तियों के क्रम की गारंटी केवल <क्वेरी एक्सप्रेशन> के लिए है जिसमें तुरंत <ऑर्डर बाय क्लॉज> होता है।"

जैसा कि उल्लेख किया गया है, टेबल एक्सप्रेशन और ऑर्डरिंग के बारे में कहने के लिए और भी बहुत कुछ है, जो मैं भविष्य के लेख में करूँगा। मैं यह प्रदर्शित करने वाले उदाहरण भी प्रदान करूंगा कि बाहरी क्वेरी में ORDER BY क्लॉज की कमी का मतलब है कि आपको कोई प्रेजेंटेशन ऑर्डरिंग गारंटी नहीं मिलती है।

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

डिजाइन की खामियां

व्युत्पन्न तालिकाओं के डिजाइन में दो मुख्य कमियां हैं। दोनों का संबंध इस तथ्य से है कि व्युत्पन्न तालिका को बाहरी क्वेरी के FROM खंड में परिभाषित किया गया है।

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

इसे प्रदर्शित करने वाला एक बहुत ही बुनियादी उदाहरण है:

आदेश का चयन करें, क्रमांक से चुनें (आदेश का चयन करें, COUNT(DISTINCT कस्टिड) से अंक के रूप में (आदेश वर्ष के रूप में चुनें (आदेश की तारीख), बिक्री से संरक्षक के रूप में। 

यह कोड ऑर्डर के वर्षों और प्रत्येक वर्ष के दौरान ऑर्डर देने वाले ग्राहकों की संख्या देता है, केवल उन वर्षों के लिए जहां ऑर्डर देने वाले ग्राहकों की संख्या 70 से अधिक थी।

यहां तालिका अभिव्यक्तियों का उपयोग करने के लिए मुख्य प्रेरणा एक कॉलम उपनाम को कई बार संदर्भित करने में सक्षम होना है। व्युत्पन्न तालिका D1 के लिए तालिका अभिव्यक्ति के रूप में उपयोग की जाने वाली अंतरतम क्वेरी Sales.Orders तालिका को क्वेरी करती है, और कॉलम नाम ऑर्डर वर्ष को अभिव्यक्ति YEAR(orderdate) को निर्दिष्ट करती है, और custid कॉलम भी लौटाती है। D1 के विरुद्ध क्वेरी क्रम वर्ष के अनुसार D1 से पंक्तियों को समूहित करती है, और ऑर्डर वर्ष के साथ-साथ उन ग्राहकों की अलग-अलग संख्या लौटाती है, जिन्होंने वर्ष के दौरान क्रमांक के रूप में उपनाम के रूप में ऑर्डर दिया था। कोड इस क्वेरी के आधार पर D2 नामक एक व्युत्पन्न तालिका को परिभाषित करता है। क्वेरी D2 की तुलना में सबसे बाहरी क्वेरी और केवल उन वर्षों को फ़िल्टर करती है जहां ऑर्डर देने वाले ग्राहकों की संख्या 70 से अधिक थी।

नेस्टिंग के कई स्तरों के कारण इस कोड की समीक्षा करने या समस्याओं के मामले में इसका निवारण करने का प्रयास मुश्किल है। ऊपर से नीचे की ओर अधिक स्वाभाविक तरीके से कोड की समीक्षा करने के बजाय, आप पाते हैं कि आपको इसका विश्लेषण अंतरतम इकाई से शुरू करना होगा और धीरे-धीरे बाहर जाना होगा, क्योंकि यह अधिक व्यावहारिक है।

इस उदाहरण में व्युत्पन्न तालिकाओं का उपयोग करने के बारे में संपूर्ण बिंदु अभिव्यक्तियों को दोहराने की आवश्यकता से बचकर कोड को सरल बनाना था। लेकिन मुझे यकीन नहीं है कि यह समाधान इस लक्ष्य को प्राप्त करता है। इस मामले में, आप शायद कुछ अभिव्यक्तियों को दोहराना बेहतर समझते हैं, व्युत्पन्न तालिकाओं का पूरी तरह से उपयोग करने की आवश्यकता से परहेज करते हैं, जैसे:

वर्ष चुनें(आदेश दिनांक) आदेशवर्ष के रूप में, COUNT(DISTINCT custid) numcustsFROM Sales.OrdersGROUP by YEAR(orderdate) वाले COUNT(DISTINCT custid)> 70;

ध्यान रखें कि उदाहरण के लिए मैं यहां एक बहुत ही सरल उदाहरण दिखा रहा हूं। नेस्टिंग के अधिक स्तरों के साथ उत्पादन कोड की कल्पना करें, और लंबे, अधिक विस्तृत कोड के साथ, और आप देख सकते हैं कि यह कैसे बनाए रखने के लिए काफी अधिक जटिल हो जाता है।

व्युत्पन्न तालिकाओं के डिजाइन में एक और दोष उन मामलों से संबंधित है जहां आपको एक ही व्युत्पन्न तालिका के कई उदाहरणों के साथ बातचीत करने की आवश्यकता होती है। एक उदाहरण के रूप में निम्नलिखित प्रश्न पर विचार करें:

CUR.orderyear, CUR.numorders, CUR.numorders चुनें - PRV.numorders as diffFROM (चुनें वर्ष (आदेश दिनांक) ऑर्डर वर्ष के रूप में, COUNT (*) बिक्री से संख्या के रूप में। वर्ष द्वारा आदेश समूह (आदेश दिनांक)) CUR LEFT के रूप में आउटर जॉइन (चुनें वर्ष (आदेश दिनांक) ऑर्डर वर्ष के रूप में, COUNT (*) बिक्री से संख्याओं के रूप में। वर्ष द्वारा ऑर्डर समूह (आदेश दिनांक)) CUR पर पीआरवी के रूप में। आदेश वर्ष =पीआरवी.आदेश वर्ष + 1;

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

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

जैसा कि मैं भविष्य के एक लेख में बताऊंगा, सीटीई, अपने डिजाइन में, इन दो दोषों को उत्पन्न नहीं करते हैं जो कि व्युत्पन्न टेबल हैं।

टेबल वैल्यू कंस्ट्रक्टर

एक टेबल वैल्यू कंस्ट्रक्टर आपको स्व-निहित स्केलर एक्सप्रेशन के आधार पर टेबल वैल्यू बनाने की अनुमति देता है। फिर आप बाहरी क्वेरी में ऐसी तालिका का उपयोग कर सकते हैं जैसे आप एक व्युत्पन्न तालिका का उपयोग करते हैं जो एक आंतरिक क्वेरी पर आधारित होती है। भविष्य के लेख में मैं पार्श्व व्युत्पन्न तालिकाओं . पर चर्चा करता हूं और सहसंबंध विस्तार से, और मैं टेबल वैल्यू कंस्ट्रक्टर्स के अधिक परिष्कृत रूप दिखाऊंगा। In this article, though, I’ll focus on a simple form that is based purely on self-contained scalar expressions.

The general syntax for a query against a table value constructor is as follows:

SELECT