कुछ विशेष पात्रों के लिए ISNUMERIC के पीछे तर्क क्या है?


14

ISNUMERICसमारोह कुछ अनपेक्षित व्यवहार है। MSDN प्रलेखन कहता है:

ISNUMERIC1 रिटर्न जब इनपुट अभिव्यक्ति एक वैध संख्यात्मक डेटा प्रकार का मूल्यांकन करता है; अन्यथा यह 0. लौटाता है। मान्य संख्यात्मक डेटा प्रकारों में निम्नलिखित शामिल हैं: int, bigint, smallint, smallint, दशमलव, संख्यात्मक, पैसा, smallmoney, float, real

और इसमें एक फुटनोट भी है:

ISNUMERICकुछ वर्णों के लिए 1 लौटाता है जो संख्या नहीं हैं, जैसे कि प्लस (+), माइनस (-), और मान्य मुद्रा प्रतीक जैसे डॉलर चिन्ह ($)। मुद्रा प्रतीकों की पूरी सूची के लिए, पैसा और स्मॉलमनी (लेनदेन-एसक्यूएल) देखें

ठीक है, इसलिए +, -और सूचीबद्ध मुद्रा प्रतीकों को संख्यात्मक माना जाता है। अब तक सब ठीक है।

अब विषम भाग के लिए। सबसे पहले, लिंक किए गए लेख में से कुछ मुद्रा प्रतीक संख्यात्मक नहीं हैं , जिनमें शामिल हैं:

  • यूरो-मुद्रा संकेत, हेक्स 20A0:
  • नायरा साइन, हेक्स 20 ए 6:
  • रियाल साइन, हेक्स एफडीएफसी:

यह अजीब है, और मुझे यह पता नहीं लग सकता है कि क्यों? क्या यह संस्करण या वातावरण निर्भर है?

हालांकि, चीजों को निराई मिलती है। यहाँ कुछ अन्य हैं जिन्हें मैं समझा नहीं सकता:

  • /संख्यात्मक नहीं है, लेकिन \है ( हुह ?! )
  • REPLICATE(N'9', 308)संख्यात्मक है, लेकिन REPLICATE(N'9', 309)नहीं है

पहला और सबसे बुनियादी सवाल यह है: उपरोक्त मामलों की व्याख्या क्या है? हालांकि अधिक महत्वपूर्ण: क्या तर्क हैISNUMERIC , इसलिए मैं सभी मामलों की व्याख्या / भविष्यवाणी कर सकता हूं?

यहाँ चीजों को पुन: पेश करने का एक अच्छा तरीका है:

DECLARE @tbl TABLE(txt NVARCHAR(1000));

INSERT INTO @tbl (txt) 
VALUES (N''), (N' '), (N'€'), (N'$'), (N'$$'), 
       (NCHAR(8356)), (NCHAR(8352)), (NCHAR(8358)), (NCHAR(65020)), 
       (N'+'), (N'-'), (N'/'), (N'\'), (N'_'), (N'e'), (N'1e'), (N'e1'), (N'1e1'), 
       (N'1'), (N'-1'), (N'+1'), (N'1+1'), (N''), (N'🄂'), (N'¹'), (N''), (N'½'), 
       (N'🎅'), (REPLICATE(N'9', 307)), (REPLICATE(N'9', 308)), (REPLICATE(N'9', 309)), 
       (REPLICATE(N'9', 310));

SELECT  UNICODE(LEFT(txt, 1)) AS FirstCharAsInt,
        LEN(txt) AS TxtLength,
        txt AS Txt,
        ISNUMERIC(txt) AS [ISNUMERIC]
FROM    @tbl;

जब मैं अपने स्थानीय Sql Server 2012 बॉक्स पर इसे चलाता हूं तो मुझे निम्नलिखित परिणाम मिलते हैं:

FirstCharAsInt   TxtLength   Txt        ISNUMERIC
---------------  ----------  ---------  ----------
NULL             0                      0
32               0                      0
8364             1           €          1
36               1           $          1
36               2           $$         0
8356             1           ₤          1
8352             1           ₠          0  --??
8358             1           ₦          0  --??
65020            1           ﷼‎          0  --??
43               1           +          1
45               1           -          1
47               1           /          0
92               1           \          1  --??
95               1           _          0
101              1           e          0
49               2           1e         0
101              2           e1         0
49               3           1e1        1
49               1           1          1
45               2           -1         1
43               2           +1         1
49               3           1+1        0
9352             1           ⒈         0
55356            2           🄂          0
185              1           ¹          0
9312             1           ①          0
189              1           ½          0
55356            2           🎅         0
57               307        /*...*/     1
57               308        /*...*/     1  --??
57               309        /*...*/     0  --??
57               310        /*...*/     0

केवल वही गलत हैं जो मुझे गलत लगते हैं, यह 0उन पांच मूल्यों के लिए झूठी रिपोर्ट करता है जो वास्तव में ठीक हैं money। दूसरे सटीक लगते हैं। SQL FIDDLE
मार्टिन स्मिथ

हालाँकि NCHAR(0) - NCHAR(65535)मुझे ११२ विसंगतियाँ दिखती हैं। जिसमें ऐसे अक्षर शामिल हैं ₁,₂,₃,4,5,6,7,8,9जो संख्यात्मक दिखते हैं, लेकिन मेरे लिए किसी भी चीज़ के लिए सफलतापूर्वक डाली नहीं हैं। फिडेल
मार्टिन स्मिथ

जवाबों:


13

विस्तृत व्यवहारों को ISNUMERICप्रलेखित नहीं किया जाता है, और शायद स्रोत कोड पहुंच के बिना किसी को भी पूरी तरह से नहीं जाना जाता है। उस ने कहा, यह हो सकता है कि व्याख्या यूनिकोड श्रेणीकरण (संख्यात्मक या नहीं) पर निर्भर करती है। समान रूप से, आपके द्वारा उल्लिखित अजीब मामले कीड़े हो सकते हैं जो पीछे की संगतता के लिए संरक्षित हैं। हाँ मुझे पता है कि पागल लगता है, लेकिन ऐसा होता है।

जैसा कि आप SQL Server 2012 का उपयोग कर रहे हैं, उपयोग करने की कोई आवश्यकता नहीं है ISNUMERIC। यदि स्ट्रिंग किसी दिए गए प्रकार के लिए परिवर्तनीय है, तो यह जांचने के लिए उपयोग TRY_CONVERTया पर्यायवाची TRY_CAST। जहां वे पर्याप्त कार्यक्षमता प्रदान करते हैं, ये बेहतर हैं TRY_PARSE, क्योंकि बाद में सीएलआर एकीकरण के माध्यम से अधिक महंगी प्रसंस्करण शामिल है।


2
और शायद पूरी तरह से स्रोत कोड के उपयोग के साथ बहुत सारे लोगों के लिए नहीं जाना जाता है। :-) काश मैं दूसरे पैराग्राफ के लिए फिर से +1 कर पाता। ISNUMERIC () काफी हद तक बेकार है क्योंकि इसका उद्देश्य यह निर्धारित करना है कि क्या कुछ को कम से कम एक संख्यात्मक प्रकार में परिवर्तित किया जा सकता है; यह जानना बहुत महत्वपूर्ण है कि आप एकल, विशिष्ट संख्यात्मक प्रकार में परिवर्तित हो सकते हैं।
हारून बर्ट्रेंड

1
@AaronBertrand ऐसे मामलों की एक महत्वपूर्ण संख्या प्रतीत होती है जहां यह उस इरादे को भी पूरा नहीं करता है।
मार्टिन स्मिथ

9

ASCII बैकस्लैश (कोड पॉइंट 5C) विंडोज के जापानी संस्करण द्वारा प्रयुक्त शिफ्ट-जेआईएस एन्कोडिंग में येन साइन (Shift) के समान कोड पॉइंट को साझा करने के लिए होता है, और कोरियाई EUC-KR में जीता हुआ साइन (₩)। इसलिए, यह मुद्रा संकेत विषय की सिर्फ एक निरंतरता है।


आह यह एक दिलचस्प सिद्धांत है। यह है moneyकि यह भी करने के लिए डाली।
मार्टिन स्मिथ


3
@ जरीन मैं डरता हूं न। जापानी के लिए अपने विंडोज इंस्टॉलेशन के लीगेसी कोड पेज को स्विच करें और आपको रास्ते मिलते हैं जैसे कि C:¥Program Files¥explorer.exe में
user47620
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.