दिलचस्प पोस्ट
XHTML को विश्लेषित करने में त्रुटि: तत्वों की सामग्री में अच्छी तरह से वर्णित वर्ण डेटा या मार्कअप होने चाहिए कैप प्रमेय में माँगोडब कहाँ खड़ा है? मैं कैसे जांचूं अगर एक HTML तत्व jQuery का उपयोग कर खाली है? जर्सी – कैसे सेवा नकली करने के लिए mysql_connect वी.एस. mysql_pconnect जावा में जेपैनेल पैडिंग अधिकतम आकार आईपैड / आईफ़ोन ऑफ़लाइन एप्लिकेशन कैश सबसे बड़ी संभव संख्या बनाने के लिए एक सूची को सॉर्ट करें जावा में HTTP शीर्षलेख एन्कोडिंग / डीकोडिंग " बच्चा पीड XXXX एक्सेग्ज सिग्नल सेगमेंटेशन फॉल्ट (11)" अपाचे में त्रुटि। लॉग सी ++ में अस्थायी जीवनभर की गारंटी है? कैसे तय करने के लिए "आपका रुबी संस्करण 1.9.3 है, लेकिन आपके Gemfile निर्दिष्ट 2.0.0" मैं int से स्ट्रिंग कैसे बदलूं? जावास्क्रिप्ट के साथ नई गुप्त विंडो कैसे खोलें? (गूगल क्रोम) किसी jQuery अजाक्स कॉल से सही मूल्य प्राप्त नहीं कर सकते

कैसे mysql में अनुक्रमिक संख्या में अंतराल को खोजने के लिए?

हमारे पास एक ऐसी तालिका है जिसके मूल्य किसी दूसरे सिस्टम से आयात किए गए थे। एक ऑटो-वेतनमान कॉलम है, और कोई डुप्लिकेट मान नहीं है, लेकिन इसमें मूल्यों में कमी नहीं है उदाहरण के लिए, इस क्वेरी को चलाना:

select count(id) from arrc_vouchers where id between 1 and 100 

100 वापस आना चाहिए, लेकिन यह 87 की बद क्या कोई ऐसी क्वेरी है जिसे मैं चला सकता हूँ जो गुम संख्याओं के मूल्यों को वापस करेगा? उदाहरण के लिए, रिकॉर्ड आईडी 1-70 और 83-100 के लिए मौजूद हो सकते हैं, लेकिन आईडी 71-82 के साथ कोई रिकॉर्ड नहीं है। मैं 71, 72, 73 आदि लौटना चाहता हूं।

क्या यह संभव है?

Solutions Collecting From Web of "कैसे mysql में अनुक्रमिक संख्या में अंतराल को खोजने के लिए?"

यहां संस्करण है जो किसी भी आकार की मेज पर कार्य करता है (केवल 100 पंक्तियों पर नहीं):

 SELECT (t1.id + 1) as gap_starts_at, (SELECT MIN(t3.id) -1 FROM arrc_vouchers t3 WHERE t3.id > t1.id) as gap_ends_at FROM arrc_vouchers t1 WHERE NOT EXISTS (SELECT t2.id FROM arrc_vouchers t2 WHERE t2.id = t1.id + 1) HAVING gap_ends_at IS NOT NULL 
  • gap_starts_at – वर्तमान अंतर में पहला आईडी
  • gap_ends_at – वर्तमान अंतराल में अंतिम आईडी

यह सिर्फ मेरे लिए 80 किमी से अधिक पंक्तियों के साथ तालिका में अंतराल खोजने के लिए काम करता है:

 SELECT CONCAT(z.expected, IF(z.got-1>z.expected, CONCAT(' thru ',z.got-1), '')) AS missing FROM ( SELECT @rownum:=@rownum+1 AS expected, IF(@rownum=YourCol, 0, @rownum:=YourCol) AS got FROM (SELECT @rownum:=0) AS a JOIN YourTable ORDER BY YourCol ) AS z WHERE z.got!=0; 

परिणाम:

 +------------------+ | missing | +------------------+ | 1 thru 99 | | 666 thru 667 | | 50000 | | 66419 thru 66456 | +------------------+ 4 rows in set (0.06 sec) 

ध्यान दें कि स्तंभों का क्रम expected और महत्वपूर्ण है।

यदि आप जानते हैं कि YourCol 1 से शुरू नहीं करता है और इससे कोई फर्क नहीं पड़ता है, तो आप प्रतिस्थापित कर सकते हैं

 (SELECT @rownum:=0) AS a 

साथ में

 (SELECT @rownum:=(SELECT MIN(YourCol)-1 FROM YourTable)) AS a 

नया परिणाम:

 +------------------+ | missing | +------------------+ | 666 thru 667 | | 50000 | | 66419 thru 66456 | +------------------+ 3 rows in set (0.06 sec) 

त्वरित और गंदे प्रश्न जो कि चाल करना चाहिए:

 SELECT a AS id, b AS next_id, (b - a) -1 AS missing_inbetween FROM ( SELECT a1.id AS a , MIN(a2.id) AS b FROM arrc_vouchers AS a1 LEFT JOIN arrc_vouchers AS a2 ON a2.id > a1.id WHERE a1.id <= 100 GROUP BY a1.id ) AS tab WHERE b > a + 1 

यह आपको उस आईडी को दिखाए जाने वाला एक टेबल दिखाएगा जिसके पास आईडी ऊपर लापता है, और next_id मौजूद है, और कितने … के बीच गायब हैं

 
 id next_id ग़लत_इनबेटिन
  1 4 2
 68 70 1
 75 87 11

100 पंक्तियों के साथ एक अस्थायी तालिका बनाएं और एक कॉलम जिसमें 1-100 मान हैं।

बाह्य इस सारणी को अपने arrc_vouchers तालिका में शामिल करें और एक स्तंभ मान चुनें जहां arr__wouchers आईडी रिक्त है।

यह अंधा कोडिंग, लेकिन काम करना चाहिए

 select tempid from temptable left join arrc_vouchers on temptable.tempid = arrc_vouchers.id where arrc_vouchers.id is null 

एक वैकल्पिक समाधान जिसके लिए एक क्वेरी की आवश्यकता है + कुछ कोड कुछ प्रसंस्करण करना होगा:

 select l.id lValue, c.id cValue, r.id rValue from arrc_vouchers l right join arrc_vouchers c on l.id=IF(c.id > 0, c.id-1, null) left join arrc_vouchers r on r.id=c.id+1 where 1=1 and c.id > 0 and (l.id is null or r.id is null) order by c.id asc; 

ध्यान दें कि क्वेरी में कोई भी उप-चयन नहीं होता है जिसे हम जानते हैं कि इसका निष्पादन MySQL के प्लानर द्वारा निष्पादन योग्य नहीं है।

यह प्रत्येक केंद्रीय मूल्य (cValue) पर एक प्रविष्टि वापस करेगा जो कि एक छोटे मूल्य (एलवीएल्यू) या अधिक मूल्य (आरवीएलयू) नहीं है, अर्थात:

 lValue |cValue|rValue -------+------+------- {null} | 2 | 3 8 | 9 | {null} {null} | 22 | 23 23 | 24 | {null} {null} | 29 | {null} {null} | 33 | {null} 

अधिक जानकारी के बिना (हम अगले पैराग्राफ में देखेंगे) इस आउटपुट का मतलब है कि:

  • 0 और 2 के बीच कोई मान नहीं है
  • 9 और 22 के बीच कोई मान नहीं है
  • 24 और 29 के बीच कोई मूल्य नहीं
  • 29 और 33 के बीच कोई मूल्य नहीं
  • 33 और MAX VALUE के बीच कोई मान नहीं है

तो बुनियादी विचार एक सही करना है और एक ही तालिका के साथ बाईं तरफ देखने में है, अगर हमारे पास प्रति मूल्य मूल्य हैं (यानी: अगर केंद्रीय मूल्य '3' है तो हम 3-1 = 2 पर बाएं और 3 + 1 पर जांचते हैं दाएं), और जब एक पंक्ति में शून्य या शून्य पर शून्य मान होता है तो हम जानते हैं कि कोई आसन्न मूल्य नहीं है

मेरी तालिका का पूरा कच्चा आउटपुट है:

 select * from arrc_vouchers order by id asc; 0 2 3 4 5 6 7 8 9 22 23 24 29 33 

कुछ नोट:

  1. एसक्यूएल अगर सम्मिलित स्थिति में वक्तव्य की आवश्यकता है यदि आप 'आईडी' फ़ील्ड को अनावृत के रूप में परिभाषित करते हैं, इसलिए यह शून्य के तहत इसे कम करने की अनुमति नहीं देगा। यह सख्ती से जरूरी नहीं है यदि आप अगले नोट में बताए गए अनुसार c.value> 0 रखते हैं, लेकिन मैं इसे डॉक्टर जैसे ही शामिल कर रहा हूं।
  2. मैं शून्य केंद्रीय मूल्य को फ़िल्टर कर रहा हूं क्योंकि हम किसी भी पिछले मान में दिलचस्पी नहीं रखते हैं और हम अगले मान से पोस्ट के मान को प्राप्त कर सकते हैं।

यदि आप MariaDB का उपयोग कर रहे हैं तो आपके पास एक तेज (800%) विकल्प है

 SELECT * FROM seq_1_to_50000 where seq not in (select col from table); 

https://mariadb.com/kb/en/mariadb/sequence/

Lucek द्वारा ऊपर दिए गए उत्तर के आधार पर इस संग्रहीत कार्यविधि से आपको तालिका और स्तंभ नामों को निर्दिष्ट करने की अनुमति मिलती है जिन्हें आप गैर-संगत रिकॉर्ड ढूंढने के लिए परीक्षण करना चाहते हैं – इस प्रकार मूल प्रश्न का उत्तर देते हुए और यह दर्शाते हुए भी कि कैसे तालिका का प्रतिनिधित्व करने के लिए @ / या एक संग्रहीत कार्यविधि में कॉलम

 create definer=`root`@`localhost` procedure `spfindnoncontiguous`(in `param_tbl` varchar(64), in `param_col` varchar(64)) language sql not deterministic contains sql sql security definer comment '' begin declare strsql varchar(1000); declare tbl varchar(64); declare col varchar(64); set @tbl=cast(param_tbl as char character set utf8); set @col=cast(param_col as char character set utf8); set @strsql=concat("select ( t1.",@col," + 1 ) as starts_at, ( select min(t3.",@col,") -1 from ",@tbl," t3 where t3.",@col," > t1.",@col," ) as ends_at from ",@tbl," t1 where not exists ( select t2.",@col," from ",@tbl," t2 where t2.",@col," = t1.",@col," + 1 ) having ends_at is not null"); prepare stmt from @strsql; execute stmt; deallocate prepare stmt; end 

यह MySQL में काम नहीं कर सकता, लेकिन काम पर (ओरेकल) हमें कुछ इसी तरह की आवश्यकता थी।

हमने एक संग्रहीत प्रोसेबल लिखा था, जिसमें अधिकतम संख्या के रूप में एक नंबर लिया गया था। संग्रहीत प्रोब ने एक स्तंभ के साथ एक अस्थायी तालिका बनाई। तालिका में सभी नंबरों को 1 से अधिकतम तक शामिल किया गया था फिर यह अस्थायी तालिका और हमारी रुचि की तालिका के बीच में शामिल नहीं किया।

यदि आप इसे max = select max (id) arrc_vouchers से कहते हैं, तो यह सभी अनुपलब्ध मूल्यों को वापस करेगा।

हालांकि ये सभी काम करने लगते हैं, परिणाम बहुत लंबे समय में रिटर्न देता है जब 50,000 रिकॉर्ड होते हैं।

मैं इसका इस्तेमाल करता था, और यह अंतर या अगले उपलब्ध उपलब्ध (अंतिम उपयोग + 1) क्वेरी से बहुत तेजी से वापसी के साथ।

 SELECT a.id as beforegap, a.id+1 as avail FROM table_name a where (select b.id from table_name b where b.id=a.id+1) is null limit 1; 

आप 1 से नंबरों को अपनी मेज के सर्वोच्च आईडी में उत्पन्न करने के लिए श्रृंखला उत्पन्न कर सकते हैं। फिर एक क्वेरी चलाएं जहां आईडी इस श्रृंखला में नहीं है।