2009-06-22 22 views
19

मेरे पास एक संग्रहीत प्रक्रिया है जो बड़ी मात्रा में डेटा के साथ काम कर रही है। मेरे पास एक डेटा तालिका में डेटा डाला जा रहा है। घटनाओं के समग्र प्रवाह जब सबसे अच्छा समय मेरी #TempTable मेज पर एक प्राथमिक कुंजी बनाने के लिए हैएक अस्थायी तालिका पर प्राथमिक कुंजी बनाना - कब?

CREATE #TempTable (
    Col1 NUMERIC(18,0) NOT NULL, --This will not be an identity column. 
    ,Col2 INT NOT NULL, 
    ,Col3 BIGINT, 

    ,Col4 VARCHAR(25) NOT NULL, 
    --Etc... 

    -- 
    --Create primary key here? 
) 


INSERT INTO #TempTable 
SELECT ... 
FROM MyTable 
WHERE ... 

INSERT INTO #TempTable 
SELECT ... 
FROM MyTable2 
WHERE ... 

-- 
-- ...or create primary key here? 

मेरा प्रश्न की तरह कुछ है? मैंने सिद्धांत दिया कि मुझे सभी डेटा डालने के बाद प्राथमिक कुंजी बाधा/अनुक्रमणिका बनाना चाहिए क्योंकि इंडेक्स को पुनर्गठित करने की आवश्यकता है क्योंकि प्राथमिक कुंजी जानकारी बनाई जा रही है। लेकिन मुझे एहसास हुआ कि मेरी रेखांकन धारणा गलत हो सकती है ...

यदि यह प्रासंगिक है, तो मेरे द्वारा उपयोग किए जाने वाले डेटा प्रकार वास्तविक हैं। #TempTable तालिका में, Col1 और Col4 मेरी प्राथमिक कुंजी बनायेगा।

अद्यतन: मेरे मामले में, मैं स्रोत तालिकाओं की प्राथमिक कुंजी को डुप्लिकेट कर रहा हूं। मुझे पता है कि मेरे प्राथमिक कुंजी को बनाए रखने वाले क्षेत्र हमेशा अद्वितीय होंगे। अगर मैं अंत में प्राथमिक कुंजी जोड़ता हूं तो मुझे असफल परिवर्तन तालिका के बारे में कोई चिंता नहीं है।

हालांकि, यह एक तरफ मेरा प्रश्न अभी भी खड़ा है, जो तेजी से मानते हैं कि दोनों सफल होंगे?

पीएस मुझे खेद है अगर यह एक डुप्लिकेट है। यह इतना बुनियादी है कि यह हो सकता है, लेकिन मुझे ऐसा कुछ भी नहीं मिला है।

उत्तर

14

यह पर निर्भर करता है।

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

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

मुझे लगता है कि समग्र त्वरित प्रदर्शन (इस प्रक्रिया का अस्थायी तालिका लोड करने के लिए) आमतौर पर डेटा को ढेर के रूप में लिखना होता है और फिर (गैर-क्लस्टर) इंडेक्स लागू होता है।

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

+1

दिलचस्प। धन्यवाद। सहायक। क्या आप शायद कुछ उदाहरणों के साथ विस्तार कर सकते हैं? क्लस्टर इंडेक्स के लिए –

+0

@ कैड, आपका मतलब डिस्क पर भौतिक क्रम है, तार्किक क्रम नहीं (तालिकाओं में तार्किक क्रम नहीं है)। –

+1

नहीं, डिस्क पर भौतिक क्रम कुछ भी हो सकता है। क्लस्टर्ड इंडेक्स केवल ढेर में एक ब्रीटी इंडेक्स में पत्तियों में संग्रहीत डेटा है। SQL सर्वर और डिस्क पर अभी भी सगाई हो सकती है। –

3

आप आवेषण से पहले प्राथमिक कुंजी भी बना सकते हैं - यदि प्राथमिक कुंजी पहचान कॉलम पर है तो आवेषण अनुक्रमिक रूप से वैसे भी किया जाएगा और इसमें कोई अंतर नहीं होगा।

+0

मैं पहचान का उपयोग नहीं करूँगा। जब आप मेरा प्रश्न अपडेट कर रहे थे तो आपने इसे पोस्ट किया था। मेरी प्राथमिक कुंजी में NUMERIC (18,0) और एक VARCHAR (25) फ़ील्ड शामिल होगा। –

+0

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

0

मुझे नहीं लगता कि यह अपने मामले में कोई महत्वपूर्ण अंतर नहीं पड़ता है:

  • या तो आप दंड एक छोटा सा एक समय में प्रत्येक एकल डालने के साथ भुगतान करते हैं,
  • या आप एक बड़ा भुगतान करेंगे सभी आवेषण के बाद जुर्माना किया जाता है, लेकिन केवल एक बार

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

लेकिन इसके अलावा - कोई बड़ा अंतर नहीं, वास्तव में।

मार्क

+1

सीमा विभाजन और लॉगिंग और सामान? इसे ध्यान में रखने की आवश्यकता नहीं है? –

1

आप जब तालिका बनाने प्राथमिक कुंजी जोड़ते हैं, तो पहले डालने मुक्त (कोई आवश्यक जाँच करता है।) हो जाएगा दूसरा डालने सिर्फ अगर यह पहले से अलग है देखने के लिए है। तीसरे डालने में दो पंक्तियों की जांच करनी है, और इसी तरह। चेक इंडेक्स लुकअप होंगे, क्योंकि जगह में एक अनूठी बाधा है।

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

लेकिन शायद एसक्यूएल सर्वर में विशिष्टता की जांच करने का एक शानदार तरीका है। तो यदि आप सुनिश्चित करना चाहते हैं, तो इसे मापें!

+0

उस बारे में नहीं सोचा था ... यह अच्छा है। –

0

मैं इसका उत्तर देने की योजना नहीं बना रहा था, क्योंकि मुझे इसके बारे में 100% आत्मविश्वास नहीं है।लेकिन चूंकि ऐसा लगता है कि आपको बहुत प्रतिक्रिया मिल रही है ...

मेरी समझ एक पीके एक अद्वितीय अनुक्रमणिका है और जब आप प्रत्येक रिकॉर्ड डालते हैं, तो आपकी अनुक्रमणिका अद्यतन और अनुकूलित होती है। तो ... यदि आप पहले डेटा जोड़ते हैं, तो अनुक्रमणिका बनाएं, इंडेक्स केवल एक बार अनुकूलित किया गया है।

तो, अगर आपको विश्वास है कि आपका डेटा साफ़ है (डुप्लिकेट पीके डेटा के बिना) तो मैं सम्मिलित कहूंगा, फिर पीके जोड़ें।

लेकिन यदि आपके डेटा में डुप्लिकेट पीके डेटा हो सकता है, तो मैं कहूंगा कि पहले पीके बनाएं, इसलिए यह ASAP को बमबारी कर देगा।

+0

आपके उत्तर के लिए धन्यवाद। वास्तव में, मुझे यकीन है कि मेरे पास डुप्लिकेट समस्या नहीं होगी ... –

1

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

यह आपको डुप्लिकेट/खराब डेटा डालने से रोकता है।

+0

यह मेरे लिए कोई समस्या नहीं है। मैं समझता हूं कि यह कुछ के लिए हो सकता है, लेकिन मेरे लिए बिल्कुल कोई समस्या नहीं है। –

+0

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

6

यदि आपके डेटाबेस का पुनर्प्राप्ति मॉडल सरल या थोक-लॉग पर सेट है, तो चुनें ... में ... यूनियन सभी सबसे तेज़ समाधान हो सकते हैं। चुनें .. INTO एक थोक ऑपरेशन है और थोक संचालन न्यूनतम लॉग इन हैं।

जैसे:

-- first, create the table 
SELECT ... 
INTO #TempTable 
FROM MyTable 
WHERE ... 
UNION ALL 
SELECT ... 
FROM MyTable2 
WHERE ... 

-- now, add a non-clustered primary key: 
-- this will *not* recreate the table in the background 
-- it will only create a separate index 
-- the table will remain stored as a heap 
ALTER TABLE #TempTable ADD PRIMARY KEY NONCLUSTERED (NonNullableKeyField) 

-- alternatively: 
-- this *will* recreate the table in the background 
-- and reorder the rows according to the primary key 
-- CLUSTERED key word is optional, primary keys are clustered by default 
ALTER TABLE #TempTable ADD PRIMARY KEY CLUSTERED (NonNullableKeyField) 

अन्यथा, कैड रॉक्स अच्छी सलाह फिर से था: पहले या बाद में।

1

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

+1

प्रश्न का संदर्भ प्राथमिक कुंजी बनाने के बारे में कम था या नहीं, लेकिन समय पर कौन सा बिंदु अधिक कुशल है - पूर्व-डेटा आबादी या बाद में डेटा आबादी। इस सवाल से पहले निष्कर्ष यह था कि एक कुंजी/सूचकांक निष्पादन समय में मदद करता था। –

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