`SELECT @@ IDENTITY` एक दशमलव क्यों लौटा रहा है?


24

मैं ASP.NET MVC 3 (.NET 4.0) अनुप्रयोग से SQL Server 2008 R2 एक्सप्रेस उदाहरण के विरुद्ध निम्न क्वेरी को निष्पादित करने के लिए Dapper का उपयोग कर रहा हूं ।

INSERT INTO Customers (
         Type, Name, Address, ContactName, 
         ContactNumber, ContactEmail, Supplier)
VALUES (
         @Type, @Name, @Address, @ContactName, 
         @ContactNumber, @ContactEmail, @Supplier)

SELECT @@IDENTITY

कॉल को connection.Query<int>(sql, ...)अमान्य कास्ट एक्सेप्शन फेंक रहा है। मैंने इसे डीबग कर लिया है और यह उस बिंदु पर है जहां डैपर ने कॉल GetValueकिया SqlDataReader

वापसी प्रकार , डिबगर शो में इसका निरीक्षण करता GetValueहै Object, यह एक बॉक्सिंग दशमलव है।

यदि मैं चयन में परिवर्तन करता हूं SELECT CAST(@@IDENTITY as int), तो GetValue की वापसी एक बॉक्सिंग इंट है और अपवाद नहीं फेंका गया है।

Id कॉलम निश्चित रूप से int का प्रकार है; एक दशमलव क्यों SELECT @@IDENTITYलौटाएगा?

कुछ अतिरिक्त जानकारी:

  • डेटाबेस एकदम नया है।
  • ग्राहक तालिका एकमात्र वस्तु है जिसे मैंने इसमें जोड़ा है। डेटाबेस में कोई अन्य (उपयोगकर्ता) टेबल, विचार, ट्रिगर या संग्रहीत कार्यविधियाँ नहीं हैं।
  • डेटाबेस में 10 पंक्तियाँ हैं, वहाँ Id 1,2,3,4,5,6,7,8,9,10 हैं (यानी कॉलम इंट की सीमा से परे नहीं है)।

मेरी तालिका परिभाषा है

CREATE TABLE [dbo].[Customers](
    [Id] [int] IDENTITY(1,1) NOT NULL,
    [Type] [int] NOT NULL,
    [Name] [nvarchar](255) NOT NULL,
    [Address] [nvarchar](1000) NOT NULL,
    [ContactName] [nvarchar](255) NOT NULL,
    [ContactNumber] [nvarchar](50) NOT NULL,
    [ContactEmail] [nvarchar](255) NOT NULL,
    [Supplier] [nvarchar](255) NOT NULL,
 CONSTRAINT [PK_Customers] PRIMARY KEY CLUSTERED 
(
    [Id] ASC
)WITH (
    PAD_INDEX  = OFF, 
    STATISTICS_NORECOMPUTE  = OFF, 
    IGNORE_DUP_KEY = OFF, 
    ALLOW_ROW_LOCKS  = ON, 
    ALLOW_PAGE_LOCKS  = ON) ON [PRIMARY]
) ON [PRIMARY]

क्या आपके पास ग्राहक तालिका पर कोई ट्रिगर है?
रिचर्ड

3
मैं @@ पहचान के बजाय SCOPE_IDENTITY () का उपयोग करूंगा । @@ पहचान आपको वर्तमान कनेक्शन पर किसी भी चीज़ द्वारा बनाई गई अंतिम पहचान मान देगी, जैसा कि आपके वर्तमान दायरे में विरोध किया गया है। इसलिए, जैसा कि रिचर्ड ने सुझाव दिया था, एक ट्रिगर एक अन्य तालिका को संशोधित करने और एक पहचान उत्पन्न करने से @@ पहचान की वापसी को प्रभावित करेगा।
निक चामास

DB में कोई ट्रिगर नहीं हैं। यह एक नया डेटाबेस है और ग्राहक तालिका एकमात्र तालिका है जिसे मैंने बनाया है।
ग्रेग बी

@Greg B: यह फ़ंक्शन का रिटर्न प्रकार है। क्या आपने रिटर्न प्रकार के रूप में int / bigint की उम्मीद की (जैसा कि सवाल बताता है) या आप इस फ़ंक्शन के लिए MS पसंद पर सवाल उठा रहे हैं?
मैरियन

जवाबों:


28
  1. @@ पहचान एक संख्यात्मक (38,0) देता है । आपको इसे इंट में लाने के लिए कास्ट करना होगा।

    चयन कास्ट (@ पहचान के रूप में INT)

  2. इसके बजाय, स्कोप_संकल्प का उपयोग करके देखें। यदि आपके पास ग्राहक तालिका में कोई ट्रिगर है, तो आप अंतिम पहचान किसी अन्य तालिका से प्राप्त कर सकते हैं।

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

    सैद्धांतिक रूप से, उन दोनों को अपने दम पर निष्पादित करने के लिए अधिकांश समय काम करना चाहिए। लेकिन समस्याएँ उत्पन्न हो सकती हैं यदि आपको डेटाबेस में दो बार जाना पड़े। (जैसे कि यह कनेक्शन पूलिंग के साथ कैसे काम करता है? गिराए गए कनेक्शन के बारे में क्या? आदि) यदि आप इसे संग्रहीत प्रक्रिया में फेंक देते हैं, तो आपको उस अतिरिक्त प्रयास के बारे में चिंता करने की ज़रूरत नहीं होगी।


# 3 के लिए धन्यवाद। क्या एक एडहॉक SQL स्टेटमेंट में बैच को परिभाषित करने का कोई तरीका नहीं है ?
ग्रेग बी

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

3
+1 SCOPE_IDENTITY () की सिफारिश के लिए
एंड्रयू बिकर्टन

10

तालिका बनाएं कहते हैं:

पहचान

इंगित करता है कि नया स्तंभ एक पहचान स्तंभ है। जब एक नई पंक्ति को तालिका में जोड़ा जाता है, तो Microsoft® SQL Server ™ कॉलम के लिए एक अद्वितीय, वृद्धिशील मूल्य प्रदान करता है। पहचान कॉलम आमतौर पर तालिका के लिए अद्वितीय पंक्ति पहचानकर्ता के रूप में सेवा करने के लिए प्राथमिक कुंजी बाधाओं के साथ संयोजन में उपयोग किया जाता है। पहचान की संपत्ति को स्मालिंट, स्मॉलिंट, इंट, बिगिंट, दशमलव (पी, 0), या संख्यात्मक (पी, 0) कॉलम को सौंपा जा सकता है। प्रति तालिका केवल एक पहचान स्तंभ बनाया जा सकता है। किसी डिफॉल्ट कॉलम के साथ बाउंड डिफॉल्ट और DEFAULT बाधाओं का उपयोग नहीं किया जा सकता है। आपको बीज और इंक्रीमेंट दोनों को निर्दिष्ट करना चाहिए और न ही। यदि न तो निर्दिष्ट किया गया है, तो डिफ़ॉल्ट (1,1) है।

बीज

क्या तालिका में लोड की गई पहली पहली पंक्ति के लिए मूल्य का उपयोग किया जाता है।

वेतन वृद्धि

क्या वृद्धिशील मूल्य पिछली पंक्ति के पहचान मूल्य में जोड़ा गया है। "

तो सिस्टम फ़ंक्शन @@ पहचान को सबसे अधिक कवर करने वाले प्रकार के साथ सामना करना होगा।


और यही कारण है कि यह numericसबसे व्यापक श्रेणी के रूप में वापस लौटता है ..? साभार
ग्रेग बी

3
एक फ़ंक्शन में एक से अधिक रिटर्न प्रकार नहीं हो सकते। इसमें हर संभावना को शामिल करने के लिए व्यापक प्रकार का उपयोग करना होगा।
मैरियन

6

"Why @ SELECT @@ IDENTITY एक दशमलव लौटाएगा"

क्योंकि इसमें फिट होने के लिए बहुत बड़ा हो सकता है int- यह पहचान कॉलम के प्रकार से मेल नहीं खाता है लेकिन जैसा कि रिचर्ड कहते हैं कि एक संख्यात्मक (38,0) रिटर्न ( numericऔर decimal समानार्थी हैं )

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.