मुझे लगता है कि मैंने इस पर SQL सर्वर में अपने ज्ञान की सीमा समाप्त कर दी है ...।
एसक्यूएल सर्वर (सी # कोड क्या करता है) में एक अंतर खोजने के लिए, और आप अंतराल को शुरू करने या समाप्त करने के बारे में परवाह नहीं करते हैं (पहली शुरुआत से पहले, या अंतिम समाप्ति के बाद), फिर निम्न क्वेरी (या वेरिएंट) है सबसे तेज़ मुझे मिल सकता है:
SELECT e.FinishedAt as GapStart, s.StartedAt as GapEnd
FROM
(
SELECT StartedAt, ROW_NUMBER() OVER (ORDER BY StartedAt) AS rn
FROM dbo.Tasks
) AS s
INNER JOIN
(
SELECT FinishedAt, ROW_NUMBER() OVER (ORDER BY FinishedAt) + 1 AS rn
FROM dbo.Tasks
) AS e ON e.rn = s.rn and s.StartedAt > e.FinishedAt
हालांकि, हाथ से थोड़ा सा काम करता है कि प्रत्येक स्टार्ट-फिनिश सेट के लिए, आप स्टार्ट और फिनिश को अलग-अलग दृश्यों के रूप में मान सकते हैं, एक से फिनिश को ऑफसेट कर सकते हैं और अंतराल दिखाए जाते हैं।
उदाहरण के लिए, (S1, F1), (S2, F2), (S3, F3), और आदेश इस प्रकार लें: {S1, S2, S3, null} और {null, F1, F2, F3} फिर पंक्ति n से पंक्ति n की तुलना करें प्रत्येक सेट में, और अंतराल ऐसे हैं जहां F सेट मान S सेट मान से कम है ... मुझे लगता है कि समस्या यह है कि SQL सर्वर में दो अलग-अलग सेटों को शामिल करने या तुलना करने का कोई तरीका नहीं है, जो कि मूल्यों के क्रम पर है सेट ... इसलिए row_number फ़ंक्शन का उपयोग हमें पंक्ति संख्या के आधार पर शुद्ध रूप से मर्ज करने की अनुमति देता है ... लेकिन SQL सर्वर को यह बताने का कोई तरीका नहीं है कि ये मान अद्वितीय हैं (उन्हें किसी इंडेक्स के साथ टेबल संस्करण में सम्मिलित किए बिना) इस पर - जो अधिक समय लेता है - मैंने इसकी कोशिश की), इसलिए मुझे लगता है कि विलय में शामिल होना इष्टतम से कम है? (हालांकि यह साबित करना मुश्किल है कि यह किसी और चीज से ज्यादा तेज है)
मैं LAG / लीड कार्यों का उपयोग करके समाधान प्राप्त करने में सक्षम था:
select * from
(
SELECT top (100) percent StartedAt, FinishedAt, LEAD(StartedAt, 1, null) OVER (Order by FinishedAt) as NextStart
FROM dbo.Tasks
) as x
where NextStart > FinishedAt
(जिस तरह से, मैं परिणामों की गारंटी नहीं देता - यह काम करने लगता है, लेकिन मुझे लगता है कि StartedAt पर निर्भर करता है ताकि कार्य तालिका में हो ... और यह धीमा था)
राशि परिवर्तन का उपयोग:
select * from
(
SELECT EventTime, Change, SUM(Change) OVER (ORDER BY EventTime, Change desc ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW) as RunTotal --, x.*
FROM
(
SELECT StartedAt AS EventTime, 1 AS Change
FROM dbo.Tasks
UNION ALL
SELECT FinishedAt AS EventTime, -1 AS Change
FROM dbo.Tasks
) AS TaskEvents
) as x
where x.RunTotal = 0 or (x.RunTotal = 1 and x.Change = 1)
ORDER BY EventTime, Change DESC
(कोई आश्चर्य नहीं, धीमी भी)
मैंने सीएलआर एग्रीगेट फंक्शन की भी कोशिश की (योग को प्रतिस्थापित करने के लिए - यह राशि की तुलना में धीमा था और डेटा के क्रम को बनाए रखने के लिए row_number () पर निर्भर था), और CLR एक टेबल वैल्यू फंक्शन (दो रिजल्ट सेट खोलने के लिए और विशुद्ध रूप से मानों की तुलना करने के लिए) अनुक्रम पर) ... और यह बहुत धीमा था। मैंने कई बार SQL, और CLR सीमाओं पर अपना सिर धमाका किया, कई अन्य तरीके आजमाए ...
और किस लिए?
एक ही मशीन पर चल रहा है, और एक सी (# मूल कोड # कोड) के अनुसार सी # डेटा, और एसक्यूएल डेटा दोनों को थूक रहा है, समय लगभग समान हैं .... 1 अंतर डेटा (सी # आमतौर पर तेजी से लगभग 2 सेकंड) ), मल्टी-गैप डेटा सेट के लिए 8-10 सेकंड (एसक्यूएल आमतौर पर तेज)।
नोट : समय की तुलना के लिए SQL सर्वर डेवलपमेंट एनवायरनमेंट का उपयोग न करें, क्योंकि यह प्रदर्शित होता है ग्रिड में समय लगता है। SQL 2012, VS2010, .net 4.0 क्लाइंट प्रोफाइल के साथ परीक्षण किया गया
मैं यह बताऊंगा कि दोनों समाधान SQL सर्वर पर डेटा की समान छँटाई करते हैं, इसलिए लाने के लिए सर्वर लोड समान होगा, जो भी समाधान आप उपयोग करते हैं, केवल ग्राहक पर प्रसंस्करण होने का अंतर (सर्वर के बजाय) , और नेटवर्क पर स्थानांतरण।
मुझे नहीं पता कि विभिन्न स्टाफ सदस्यों द्वारा विभाजन करते समय क्या अंतर हो सकता है, या जब आपको गैप सूचना के साथ अतिरिक्त डेटा की आवश्यकता हो सकती है (हालांकि मैं स्टाफ आईडी के अलावा किसी और के बारे में नहीं सोच सकता हूं), या निश्चित रूप से SQL सर्वर और क्लाइंट मशीन (या एक धीमी क्लाइंट) के बीच एक धीमा डेटा कनेक्शन है ... न ही मैंने कई उपयोगकर्ताओं के लिए लॉक-टाइम, या विवाद के मुद्दों, या CPU / NETWORK मुद्दों की तुलना की है ... इसलिए मैंने पता नहीं कौन सा इस मामले में अड़चन होने की अधिक संभावना है।
मुझे क्या पता है, हां, SQL सर्वर इस तरह की सेट तुलनाओं में अच्छा नहीं है, और यदि आप क्वेरी नहीं लिखते हैं तो आप इसके लिए भुगतान करेंगे।
क्या सी # संस्करण लिखना आसान या कठिन है? मुझे पूरा यकीन नहीं है, चेंज +/- 1, टोटल सॉल्यूशन रन करना पूरी तरह से सहज भी नहीं है, और मैं लेकिन यह पहला सॉल्यूशन नहीं है कि एक औसत ग्रेजुएट आएगा ... एक बार किया तो यह कॉपी करना काफी आसान है, लेकिन यह पहली जगह में लिखने के लिए अंतर्दृष्टि लेता है ... वही SQL संस्करण के लिए कहा जा सकता है। कौन सा कठिन है? डेटा को दुष्ट करने के लिए कौन सा अधिक मजबूत है? समानांतर संचालन के लिए कौन सी क्षमता अधिक है? क्या यह वास्तव में मायने रखता है जब प्रोग्रामिंग प्रयास की तुलना में अंतर इतना छोटा है?
एक आखिरी नोट; डेटा पर एक अस्थिर बाधा है - StartAAt समाप्तएट से कम होना चाहिए, या आपको खराब परिणाम मिलेगा।