क्या है ?[]? C # में वाक्य रचना?


85

जब मैं पढ़ाई कर रहा था प्रतिनिधि जो है वास्तव में एक अमूर्त वर्ग Delegate.cs, मैंने देखा कि निम्न विधि है, जिसमें मुझे समझ नहीं आता

  • वापसी मूल्य का उपयोग क्यों किया जाता है, ?हालांकि यह पहले से ही एक संदर्भ ( वर्ग ) प्रकार है
  • ?[]? पैरामीटर पर अर्थ

क्या आप समझाएँगे?

public static Delegate? Combine(params Delegate?[]? delegates)
{
    if (delegates == null || delegates.Length == 0)
        return null;

    Delegate? d = delegates[0];
    for (int i = 1; i < delegates.Length; i++)
        d = Combine(d, delegates[i]);

    return d;
}


23
क्या यह एक अशक्त सरणी नहीं है जिसमें अशक्त मूल्य हो सकते हैं?
Cid

3
c # 8, अब आप निर्दिष्ट कर सकते हैं कि ऑब्जेक्ट चर को शून्य होने की अनुमति नहीं है। आपको लगता है कि संकलक झंडा फ्लिप हैं, तो आप हर चर कि स्पष्ट करना पड़ता है अशक्त होने की अनुमति।
जेरेमी लक्ष्मण

जवाबों:


66

कदम से कदम स्पष्टीकरण:

params Delegate?[] delegates - यह अशक्त की एक सरणी है Delegate

params Delegate?[]? delegates - संपूर्ण सरणी अशक्त हो सकती है

चूंकि प्रत्येक पैरामीटर प्रकार का होता है Delegate?और आप Delegate?[]?एरे का एक इंडेक्स वापस करते हैं , तो यह समझ में आता है कि रिटर्न टाइप Delegate?अन्यथा अन्यथा कंपाइलर एक त्रुटि लौटाता है जैसे कि आप रिट्रीट कर रहे थेint एक विधि से जो एक स्ट्रिंग लौटाता है।

आप उदाहरण के लिए अपने कोड को Delegateइस प्रकार बदलने के लिए बदल सकते हैं :

public static Delegate Combine(params Delegate?[]? delegates)
{
    Delegate defaulDelegate = // someDelegate here
    if (delegates == null || delegates.Length == 0)
        return defaulDelegate;

    Delegate d = delegates[0] ?? defaulDelegate;
    for (int i = 1; i < delegates.Length; i++)
        d = Combine(d, delegates[i]);

    return d;
}

4
मेरे पहले सवाल का क्या? वापसी मान का उपयोग क्यों किया जाता है, ?हालांकि यह पहले से ही संदर्भ (वर्ग) प्रकार
एसएनआर - मोनिका

2
क्योंकि आप डी वापस आ रहे हैं जो डेलिगेट है? प्रकार। और मापदंडों के आधार पर अशक्त या डेलिगेट भी
Athanasios Kataras

2
@snr रिटर्न मान ?उसी कारण का उपयोग करता है जिस कारण तर्क मान उपयोग करता है ?। यदि आप उत्तरार्द्ध को समझते हैं, तो आप स्वचालित रूप से पूर्व को समझते हैं। क्योंकि विधि अशक्त लौट सकती है , जैसे पैरामीटर अशक्त को स्वीकार कर सकता है । यही है, वे दोनों शून्य हो सकते हैं
GSerg

2
मैंने उसे छुआ। मैंने उदाहरण के साथ इसे दूसरे भाग के रूप में उत्तर दिया। Since each parameter is of the type Delegate? and you return an index of the Delegate?[]? array, then it makes sense that the return type is Delegate?
अथानासियोस कतरास

2
@ एसएसएन: रिटर्न वैल्यू का उपयोग क्यों किया जाता है? हालांकि यह पहले से ही संदर्भ (वर्ग) प्रकार है (1) यह एक आदत या एक रीफ्रैक्टिंग अवशेष हो सकता है यदि समान कोड (2) में भी स्ट्रक्चर्स का उपयोग किया जाता है। C # 8 संदर्भ प्रकारों में स्वाभाविक रूप से अशक्त होने के लिए अस्वीकृत किया जा सकता है (इस प्रकार स्पष्ट अशक्तता () 3) के Foo?पास एक साफ-सुथरी HasValueसंपत्ति है, जबकि जाँच Fooकरने की आवश्यकता == nullहै (4) यह उन डेवलपर्स से संपर्क करता है जो विधि हस्ताक्षर को पढ़ते हैं, जो संभव है, अशक्त होने की उम्मीद है, और सही परिणाम हैं। (5) कोड किसी ऐसे व्यक्ति द्वारा लिखा जाना प्रतीत होता है। अशक्तता का बहुत शौकीन है और इसके बारे में स्पष्ट है।
23

25

अशक्त संदर्भ प्रकार C # 8.0 में नए हैं, वे पहले मौजूद नहीं हैं।

यह प्रलेखन की बात है, और संकलन-समय पर चेतावनी कैसे उत्पन्न होती है।

अपवाद "ऑब्जेक्ट ऑब्जेक्ट की आवृत्ति के लिए सेट नहीं है" अपवाद शांत सामान्य है। लेकिन यह एक रनटाइम अपवाद है, यह आंशिक रूप से पहले से ही संकलन समय पर खोजा जा सकता है।

एक विनियमन के लिए Delegate dआप हमेशा कॉल कर सकते हैं

 d.Invoke();

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

जबकि एक नए Delegate? pइस कोड के लिए

 p.Invoke();

एक संकलक चेतावनी का उत्पादन करेगा। CS8602: Dereference of a possibly null reference जब तक आप लिखते हैं:

 p?.Invoke();

क्या मतलब है, केवल अगर अशक्त नहीं है।

तो आप एक चर का दस्तावेज शून्य या नहीं हो सकता है। यह पहले चेतावनी देता है और यह अशक्त के लिए कई परीक्षणों से बच सकता है। वही जो आपके पास int और int के लिए है। आप निश्चित रूप से जानते हैं, एक शून्य नहीं है - और आप जानते हैं कि एक को दूसरे में कैसे परिवर्तित किया जाए।


उस चेतावनी के साथ जिसे आप निश्चित रूप से नहीं जानते हैं कि Delegateयह अशक्त नहीं है। आप सिर्फ यह दिखावा करते हैं कि आप निश्चित रूप से जानते हैं (जो कि ज्यादातर मामलों में काफी अच्छा है)।
टिम पोहल्मन

@TimPohlmann साथ ही int i = null असंभव है, एक स्ट्रिंग s = null असंभव है (इस ब्रेकिंग चेंज के साथ C # 8 में)। तो यह कुछ दिखावा करने की तुलना में थोड़ा अधिक है। पिछड़े संगतता के लिए यह एक चेतावनी के लिए डाउनग्रेड है। यदि आप चेतावनी को किसी त्रुटि पर अपग्रेड करते हैं, तो आप जानते हैं कि यह शून्य नहीं है।
Holger

4
पिछली बार मैंने एनआरटी की जांच की थी कि यह 100% बुलेट प्रूफ नहीं है। कुछ ऐसे किनारे मामले हैं जिनका कंपाइलर पता नहीं लगा सकता है।
टिम पोहलमैन

हां, लेकिन यह "वैरिएबल इनिशियलाइज्ड नहीं" या "सभी कोड रास्तों के लिए एक मान लौटाता है" चेतावनी के समान है। रनटाइम पर पता लगाने के बिना, सभी 100% संकलन-समय की विशेषताएं हैं। Int के विपरीत ?, मुझे लगता है कि वे अतिरिक्त जानकारी रखने के लिए अतिरिक्त मेमोरी नहीं जोड़ते हैं। तो चलिए बताते हैं कि यह इंटेलीजेंस जितना विश्वसनीय है। काफी अच्छा।
होल्गर

1
यदि आपके पास intयह है तो कभी भी अशक्त नहीं हो सकता। यदि आपके पास Delegateयह शून्य है (विभिन्न कारणों से, जैसे प्रतिबिंब)। यह आमतौर पर यह मान लेना सुरक्षित है कि Delegate(C # 8 में NRT सक्षम के साथ) शून्य नहीं है, लेकिन आप कभी भी सुनिश्चित करने के लिए नहीं जानते हैं (जहां intहम सुनिश्चित करने के लिए जानते हैं)।
टिम पोहल्मन

5

C # 8 में स्पष्ट रूप से संदर्भ प्रकारों को अशक्त के रूप में चिह्नित करना चाहिए।

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

दिए गए कोड को C # 8 के साथ काम करने के लिए फिर से शुरू किया गया है, लेकिन यह इस नई सुविधा से लाभ नहीं करता है।

public static Delegate? Combine(params Delegate?[]? delegates)
{
    // ...[]? delegates - is not null-safe, so check for null and emptiness
    if (delegates == null || delegates.Length == 0)
        return null;

    // Delegate? d - is not null-safe too
    Delegate? d = delegates[0];
    for (int i = 1; i < delegates.Length; i++)
        d = Combine(d, delegates[i]);

    return d;
}

इस सुविधा का लाभ उठाते हुए एक अद्यतन कोड (काम नहीं, सिर्फ एक विचार) का एक उदाहरण है। इसने हमें अशक्त होने से बचाया और इस पद्धति को थोड़ा सरल बनाया।

public static Delegate? Combine(params Delegate[] delegates)
{
    // `...[] delegates` - is null-safe, so just check if array is empty
    if (delegates.Length == 0) return null;

    // `d` - is null-safe too, since we know for sure `delegates` is both not null and not empty
    Delegate d = delegates[0];

    for (int i = 1; i < delegates.Length; i++)
        // then here is a problem if `Combine` returns nullable
        // probably, we can add some null-checks here OR mark `d` as nullable
        d = Combine(d, delegates[i]);

    return d;
}

2
those types are not able to contain null, ध्यान दें कि यह संकलक चेतावनी उत्पन्न करता है , त्रुटि नहीं। कोड ठीक चलेगा (हालाँकि यह NullReferenceException उत्पन्न कर सकता है)। यह मन में पीछे की संगतता के साथ किया जाता है।
JAD
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.