2014-09-28 8 views
14

किसी प्रोटोकॉल की वैकल्पिक प्रॉपर्टी कैसे सेट करता है? उदाहरण के लिए UITextInputTraits में कई वैकल्पिक रीड/राइट गुण हैं। आम तौर पर जब एक प्रोटोकॉल आप एक प्रश्न चिह्न जोड़ें का एक वैकल्पिक प्रॉपर्टी एक्सेसस्विफ्ट: प्रोटोकॉल की वैकल्पिक संपत्ति सेट करना

func initializeTextInputTraits(textInputTraits: UITextInputTraits) { 
    textInputTraits.keyboardType = .Default 
} 

लेकिन यह काम नहीं करता: जब मैं निम्नलिखित की कोशिश मैं एक संकलन त्रुटि मिलती है ('textInputTraits' में 'keyboardType' के लिए आवंटित नहीं कर सकते हैं) जब एक मूल्य बताए

textInputTraits.keyboardType? = .Default 

प्रोटोकॉल लगता है: (त्रुटि: इस अभिव्यक्ति के परिणाम के लिए आवंटित नहीं किया जा सकता) (? अभी तक)

protocol UITextInputTraits : NSObjectProtocol { 
    optional var keyboardType: UIKeyboardType { get set } 
} 

उत्तर

9

स्विफ्ट में असंभव है । एक ADF thread से संदर्भित

Optional property requirements, and optional method requirements that return a value, will always return an optional value of the appropriate type when they are accessed or called, to reflect the fact that the optional requirement may not have been implemented.

So it's no surprise to get optional values easily. However, setting a property requires implementation to be guaranteed.

+0

स्विफ्ट 2.2 – adib

+0

के रूप में अभी भी असंभव है स्विफ्ट 4 – Speakus

+0

और एक अच्छे कारण के लिए अभी भी असंभव है। 'वैकल्पिक func setSomething (_ :) 'का उपयोग करें। – akashivskyy

3

एक वैकल्पिक हल एक और प्रोटोकॉल है कि पहले एक के अनुरूप बनाने के लिए है, लेकिन यह है कि अनिवार्य रूप में है कि वैकल्पिक संपत्ति की घोषणा। फिर ऑब्जेक्ट को उस नए प्रोटोकॉल के रूप में डालने का प्रयास करने के लिए, और यदि कलाकार सफल होता है, तो हम सीधे संपत्ति तक पहुंच सकते हैं।

protocol UITextInputTraitsWithKeyboardType : UITextInputTraits { 
    // redeclare the keyboardType property of the parent protocol, but this time as mandatory 
    var keyboardType: UIKeyboardType { get set } 
} 

func initializeTextInputTraits(textInputTraits: UITextInputTraits) { 
    // We try to cast ('as?') to the UITextInputTraitsWithKeyboardType protocol 
    if let traitsWithKBType = textInputTraits as? UITextInputTraitsWithKeyboardType { 
    // if the cast succeeded, that means that the keyboardType property is implemented 
    // so we can access it on the casted variable 
    traitsWithKBType.keyboardType = .Default 
    } 
    // (and if the cast failed, this means that the property is not implemented) 
} 

मैं भी दिखा दिया कि at the bottom on this SO answer आप विचार का एक और उदाहरण चाहते हैं।

+0

मैंने स्विफ्ट 2.2 के साथ यह कोशिश की, लेकिन जैसा? नहीं ले रहा है - मुझे याद है कि प्रोटोकॉल वास्तव में उनके नाम से मूल्यांकन किया जाता है। यदि मूल ऑब्जेक्ट ने "UITextInputTraitsWithKeyboardType" लागू नहीं किया है तो यह पास नहीं होगा। आश्चर्य है कि आपको यह काम करने के लिए कैसे मिला ... –

6

मैं keyboardType के लिए अपना डिफ़ॉल्ट मान वापस करने का विस्तार करने पर विचार करता हूं, और सेटटर कुछ भी नहीं करता है।

extension UITextInputTraits { 
    var keyboardType: UIKeyboardType { 
     get { return .Default } 
     set(new){ /* do nothing */ } 
    } 
} 

इस तरह आप अपनी संपत्ति घोषणा से optional निकाल सकते हैं।

protocol UITextInputTraits : NSObjectProtocol { 
    var keyboardType: UIKeyboardType { get set } 
} 

या, यदि आप चाहें, तो आप यह वैकल्पिक वापसी प्रकार, var keyboardType: UIKeyboardType? के कर सकते हैं और nil बजाय .Default लौटने अपने विस्तार में।

इस प्रकार, आप यह देखने के लिए myObject.keyboardType == nil पर परीक्षण कर सकते हैं कि आपकी संपत्ति लागू की गई है या नहीं।

0

निम्नलिखित क्या मैं के साथ आया था स्विफ्ट 2.2 संगतता के लिए किया जाता है:

@objc protocol ComponentViewProtocol: class { 
    optional var componentModel: ComponentModelProtocol? { get set } 
    optional var componentModels: [String:ComponentModelProtocol]? { get set } 
} 

class ComponentView: NSObject, ComponentViewProtocol { 
    var componentModel: ComponentModelProtocol? 
    ... 
    .. 
    . 
} 

class SomeCodeThatUsesThisStuff { 

    func aMethod() { 
     if var componentModel = componentView.componentModel { 
      componentModel = .... (this succeeds - you can make assignment) 
     } else if var componentModels = componentView.componentModels { 
      componentModels = .... (this failed - no assignment possible) 
     } 
    } 
} 

संक्षेप में आप एक वैकल्पिक संपत्ति पर "/ बाध्यकारी चलिए देखते हैं" सुनिश्चित करने के लिए यह वास्तव में कार्यान्वित किया जाता है प्रदर्शन करने की जरूरत है? यदि यह शून्य है तो encapsulating ऑब्जेक्ट इसे लागू नहीं किया है, लेकिन अन्यथा अब आप इसे असाइनमेंट कर सकते हैं और संकलक अब शिकायत नहीं करेगा।

+0

यह आपके द्वारा बनाए गए स्थानीय चर को बदलता है - यह ऑब्जेक्ट वैल्यू को नहीं बदलता है। –

संबंधित मुद्दे