स्विफ्ट IF LET का मूल्यांकन कैसे किया जाता है?


86

मैंने स्विफ्ट साइट और विभिन्न पदों पर इस कोड को देखा है और मैं मूल बातें समझने की कोशिश कर रहा हूं। इस रेखा का मूल्यांकन कैसे किया जाता है?

if let name = optionalName {

मैं उलझन में हूं क्योंकि यह नाम == वैकल्पिक नाम नहीं है, यह मान प्रदान कर रहा है, इसलिए यह रिपोर्ट कैसे सच है और यह सच क्यों नहीं है जब आप जॉइन की जगह शून्य से सराहना करते हैं, क्योंकि यह अभी भी बराबर होने जा रहा है?

var optionalName: String? = "John Appleseed"
var greeting = "Hello!"
if let name = optionalName {
    greeting = "Hello, \(name)"
}

10
स्विफ्ट प्रलेखन में लुकअप "वैकल्पिक बाध्यकारी" ...
मार्टिन आर

3
एक विस्तृत विकल्प dev.iachieve.it/iachieveit/?p=314 पर देखा गया , if letवाक्यविन्यास को वैकल्पिक बंधन के रूप में जाना जाता है।
जो

जवाबों:


100

अनिवार्य रूप से लाइन कह रही है, "यदि आप नए चर nameको गैर-वैकल्पिक संस्करण के बराबर कर सकते हैं optionalName, तो इसके साथ निम्नलिखित करें"। जैसा कि मार्टिन ने बताया, इसे वैकल्पिक बंधन कहा जाता है ।

इसका एकमात्र उद्देश्य यह है कि यदि एक वैकल्पिक चर में एक वास्तविक मूल्य है और गैर-वैकल्पिक रूप को एक अस्थायी चर से बांधता है। यह वैकल्पिक या दूसरे शब्दों में "अनचेक" करने का सुरक्षित तरीका है, वैकल्पिक में निहित मूल्य तक पहुंचें। यह किसी भी तरह की समानता के लिए परीक्षण नहीं है। यह केवल एक वैकल्पिक के भीतर एक मूल्य के अस्तित्व के लिए परीक्षण कर रहा है।


1
मैं उस के बारे में पढ़ा होगा जब मैं इसे करने के लिए नीचे उतरो, मैं बस तेजी से परिचय की शुरुआत पर और यह यह नहीं समझाता। आप स्पष्टीकरण सही समझ में आता है, धन्यवाद।
डेडजेरो

1
वैकल्पिक चर का मान होने पर हमें "if" की जगह "if" का उपयोग क्यों नहीं करना चाहिए - अगर वैकल्पिक नाम है! = Nil {ग्रीटिंग = "हैलो, (नाम)"}
Nuibb

4
@ निब इसलिए क्योंकि जब if letहम उपयोग करते हैं तो मान को गैर-वैकल्पिक चर nameमें बाँधते हैं ( इस उदाहरण में)। आपका उदाहरण संकलित नहीं किया जाएगा क्योंकि अब कोई चर नहीं है name। यदि आपने optionalNameइसका उपयोग करने के लिए अपना उदाहरण बदल दिया है तो इसे प्रिंट आउट के रूप में किया जाएगा Hello, Optional("John Appleseed")। आप शून्य के खिलाफ जाँच के बाद जबरन अलिखित का उपयोग कर सकते हैं, Hello, \(optionalName!)लेकिन यदि आप चेक के बिना उस खंड के कोड को कहीं स्थानांतरित करते हैं तो यह अधिक त्रुटि वाला है।
drewag

29

एक वैकल्पिक या तो सेट है या नहीं-सेट (शून्य या शून्य नहीं) ... हमें एक महत्वपूर्ण निर्णय के साथ छोड़ रहा है। "हमें अपना कोड कैसे लिखना चाहिए ताकि यह दोनों राज्यों के लिए सही तरीके से काम कर सके?"। जिस तरह से हम वैकल्पिक को खोलते हैं वह वही है जो हमारे लिए तय करता है।

कई दृष्टिकोण हैं जो आप एक वैकल्पिक सेट का मुकाबला करने के लिए उपयोग कर सकते हैं।

  • दुर्घटना!
  • मान को किसी चीज़ में डिफ़ॉल्ट करें - यदि वह सेट नहीं था।
  • सुंदर रूप से असफल रहें या कुछ भी न करें, लेकिन अगर मूल्य निर्धारित किया गया था, तो इसे असाइन करें।
  • ग्रेसफुल फेल यानी कुछ भी न करें, हालांकि अगर मूल्य निर्धारित किया गया था ... कुछ करें (यह सिर्फ एक असाइनमेंट से अधिक है)।

नीचे 4 दृष्टिकोण हैं


यदि आपके पास कोई मान नहीं है, तो जबरन अपरिवर्तित उपयोग करना क्रैश हो जाएगा । आप ऐसा करना चाहते हैं यदि उस मूल्य का महत्वपूर्ण महत्व है जैसे कि फिल्म का शीर्षक (हर फिल्म का एक नाम होना चाहिए)। !का उपयोग जबरन उतारने के लिए किया जाता है।

movieTitle = movie.title!

Nil coalescing का उपयोग एक और तरीका है जो आपको अधिक नियंत्रण प्रदान करेगा , जिसका अर्थ है कि यह दुर्घटनाग्रस्त नहीं होगा यदि मूल्य निर्धारित नहीं किया गया है, और न ही इसे 'कुछ भी सेट नहीं किया जाएगा' यदि यह सेट नहीं है ... तो यह वही होगा जो आप इसे बताएंगे ऐसा करने के लिए, अगर यह कोई नाम सेट नहीं था, तो इसे मूवी का नाम डिफ़ॉल्ट रूप से सेट किया जाएगा । ??nil coalescing के लिए प्रयोग किया जाता है।

var movieTitle = movie.title ?? "untitled_Movie"

यदि आपके पास कोई मान नहीं है, तो वैकल्पिक चैनिंग का उपयोग करने से कुछ नहीं होगा और यदि आपके पास कोई मान है, तो मान सेट करेगा । आप ऐसा कुछ करते हैं कि आपके अभिनेता के एजेंट के नाम के लिए उसका मूल्य निर्धारित होना महत्वपूर्ण नहीं है । वैकल्पिक श्रृंखलन के लिए उपयोग किया जाता है।?

let agent = movie.leadActor?.agent //would not crash if you don't have a lead actor (optional chaining)
let agent = movie.leadActor!.agent //would crash if you don't have a lead Actor (forced wrapping)  

का उपयोग करते हुए if-let(या guardजिनमें से दो विभिन्न प्रकार हैं वैकल्पिक बाध्यकारी ) आप दे देंगे और अधिक नियंत्रण है, यह अगर मूल्य सेट नहीं है क्रैश नहीं करेंगे। यदि मान सेट है, तो आप कुछ कर सकते हैं। यदि यह सेट नहीं है तो आप एक elseबयान जोड़ सकते हैं ।

if let supportingActor = movie.supportingActor{
print(" The supporting actor is \(supportingActor)}

यह अलौकिकता का सबसे अधिक इस्तेमाल किया जाने वाला तरीका है, क्योंकि जबरन अलिखित करना कुछ हद तक हतोत्साहित करता है। इसे हतोत्साहित करने के बारे में अधिक चर्चा के लिए यहाँ देखें । के बीच एक अच्छी तुलना के लिए guardऔर if-letदेखेंguard vs. if-let


पक्षीय लेख:

वैकल्पिक बाइंडिंग और वैकल्पिक श्रृंखलन आमतौर पर एक साथ उपयोग किए जाते हैं:

if let agent = movie.leadActor?.agent {
ContactInfo = agent.phoneNumber
} // if-let is the optional *binding* part, the movie dot leadActor dot is the optional *chaining*
 

क्यों बेवजह को मजबूर किया जाएगा, ऐसी स्थिति को देखते हुए हतोत्साहित किया जाए जहां फिल्मटाइटल कभी भी एक तार के अलावा और कुछ नहीं हो सकता है, और सभी तार मूवीटील के लिए मान्य हैं? (और मैं नहीं चाहता कि "अनटाइटल्ड मूवी" आई वांट "") इस स्थिति के लिए मजबूर अल्ट्रापॉपिंग एकमात्र सही तरीका है, यह बहुत अच्छा होगा यदि आप उस हिस्से को हटा सकते हैं जो कहता है कि "मजबूर अलिखित कुछ हतोत्साहित" है क्योंकि यह गलत जानकारी है ।
एंडी

मान लीजिए कि आप एक नेटवर्क कॉल करते हैं और सर्वर टीम के कुछ डेवलपर ने एक बुरा निर्णय लिया और फिल्में शीर्षक भेजना भूल गए। क्या आप चाहते हैं कि आपका ऐप उत्पादन में क्रैश हो जाए? या सिर्फ अज्ञात शीर्षक लिखें? तथ्य की बात के रूप में IMDb पर कुछ फिल्में शीर्षक नहीं है :)। इसके अतिरिक्त बल का अर्थ है कि आपने कोई लॉगिंग या दावा नहीं किया है। यह बुरी बात है। क्योंकि आपको पता नहीं होगा कि मूल कारण क्या था।
हनी

यह एक पुआल आदमी का तर्क है, मैंने कभी नहीं कहा "हमेशा मजबूर अलौकिक का उपयोग करें।" सिर्फ इसलिए कि आपको अपने उदाहरण में जबरन अलिखित का उपयोग नहीं करना चाहिए, इसका अर्थ यह नहीं है कि प्रत्येक उदाहरण में जबरन अलिखित को हतोत्साहित नहीं किया जाता है। मैंने आपको एक ऐसा परिदृश्य दिया, जहां आपके द्वारा प्रस्तुत चार में से केवल एक ही समाधान है। क्या आप मेरी पिछली टिप्पणी में बताए गए परिदृश्य का बेहतर समाधान दे सकते हैं? यदि नहीं, तो कृपया अपनी टिप्पणी को "बिना सोचे समझे हतोत्साहित करना" के बारे में अपनी टिप्पणी को संशोधित करने पर विचार करें क्योंकि यह संदर्भ पर विचार किए बिना कुछ हतोत्साहित नहीं है।
एंडी

यदि आप कुछ "डिफ़ॉल्ट" कर रहे हैं तो यह अब एक वैकल्पिक नहीं है
हनी

उदाहरण के लिए, "" मूल्य स्टोरीबोर्ड में बनाई गई एक यूआईबेल उदाहरण की पाठ संपत्ति से आ रहा है, यह एक वैकल्पिक है क्योंकि यह शून्य हो सकता है यदि आप इसे गतिशील रूप से बनाते हैं, लेकिन यहां आप इसे गतिशील रूप से नहीं बना रहे हैं, इसलिए इसमें हमेशा एक स्ट्रिंग मान होगा । क्या आप इस मामले में जबरन उपयोग नहीं करने जा रहे हैं, इसके बजाय, आप if-let से अनचाहे और एक मान प्रदान करेंगे जो इसके डिफ़ॉल्ट मान के समान है ""? आप कर सकते हैं, लेकिन यह व्यर्थ, अनावश्यक और चिंताजनक है। और क्या होगा अगर आप एक HTTP लाइब्रेरी का उपयोग कर रहे हैं जो कि एक त्रुटि होने पर भी हमेशा एक शब्दकोश लौटाएगा। यह संदर्भ-निर्भर है।
एंडी

4

अगर सिंटैक्स 2 अलग-अलग शर्तों को स्वीकार करता है। दूसरा, एक वैकल्पिक बंधन, एक बूलियन नहीं है। यह भ्रामक है, जैसा कि आप लिख सकते हैं:

if let name = optionalName {

लेकिन नहीं

if (let name = optionalName) {

Apple प्रलेखन (स्विफ्ट संदर्भ):

हालत का मूल्य प्रकार का होना चाहिए Boolया एक प्रकार का होना चाहिए Bool। हालत भी एक वैकल्पिक बाध्यकारी घोषणा, के रूप में में चर्चा हो सकती है वैकल्पिक बाइंडिंग


3

if केवल बूलियन अभिव्यक्ति लेता है, इसके अलावा यह एक त्रुटि फेंक देगा, इसलिए यह कोड स्निपेट कह रहा है

if let name = optionalName {

}else{

}

यदि वैकल्पिक नाम शून्य है, तो स्थिति झूठी है और अन्य विवरण निष्पादित करेगा। हालाँकि अगर वैकल्पिकनाम का कुछ मूल्य है तो वैकल्पिक मान को अपरिवर्तित / स्थिर चर में निर्दिष्ट किया जाता है।


1

जब भी आप कमजोर संदर्भों के साथ काम कर रहे हैं , तो वैकल्पिक प्रकारों का उपयोग करना बेहतर होगा यदि अपने कोड को सुरक्षित रखने दें और क्रैश से बचने के लिए यहां उदाहरण हैं

var middleName :String? = "some thing"
if let isExistsMiddleName = middleName {
// do some thing here
} else {
// no middle name
}
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.