【问题标题】:Class Init with Optional Parameters - not possible?带有可选参数的类初始化 - 不可能?
【发布时间】:2018-04-06 08:54:48
【问题描述】:

谁能帮我理解为什么我无法将 middleName 参数设置为一个值?我已经将它声明为一个可选的,但是每当我尝试初始化它时,我总是在 getFullName() 函数中的保护语句中运行 nil。

var firstName: String
var middleName: String?
var lastName: String

init(firstName: String, middleName: String, lastName: String)
{
    self.firstName = firstName
    self.middleName? = middleName
    self.lastName = lastName
}

func getFullName() -> String
{        
    guard let midName = self.middleName else
    {
        return "\(firstName) \(lastName)"
    }

    return "\(firstName) \(midName) \(lastName)"
}

let person = Person(firstName: "Foo", middleName: "Bar", lastName: "FooBar")

打印时的返回值为“Foo Foobar”。这是为什么?

【问题讨论】:

    标签: swift


    【解决方案1】:

    在分配属性时,您不需要(或不想)解开该属性。你直接引用就行了;

    init(firstName: String, middleName: String, lastName: String)
    {
        self.firstName = firstName
        self.middleName = middleName
        self.lastName = lastName
    }
    

    middleNamenil(最初是这样)时,条件解包self.middleName? 失败,因此不执行分配。

    有条件地展开 self.middleName 实际上是一种简写方式

    if self.middleName != nil {
        self.middleName = middleName
    }
    

    由于middleName 是可选的,那么您可能希望初始化参数也可选:

    init(firstName: String, middleName: String?=nil, lastName: String)
    {
        self.firstName = firstName
        self.middleName = middleName
        self.lastName = lastName
    }
    

    【讨论】:

    • 非常感谢您的解释!我真的很感激。
    • 快速提问:当您说“您只是引用它”时,您所说的“它”到底是什么意思?你的意思是self.middleName 属性引用了middleName 参数(“it”部分)?
    • “它”是属性middleName。你不需要?。与?您正在访问属性的值,而不是属性。
    • 抱歉,我自己可能搞糊涂了。这对我来说很新鲜。那么,middleName 是在分配之前还是之后?
    • self.middleName 是一个属性。当您说 self.middleName? 时,您是在对 Swift 说“有条件地展开 self.middleName” - 有条件地展开是说 if self.middleName != nil { self.middleName=middleName } 的简写方式
    【解决方案2】:

    如果一个属性是可选的,你必须让init方法中的相应参数也是可选的,否则将属性声明为可选是没有意义的。

    init(firstName: String, middleName: String?, lastName: String)
    {
        self.firstName = firstName
        self.middleName = middleName
        self.lastName = lastName
    }
    

    您甚至可以将nil 指定为默认值 以便能够省略参数

    init(firstName: String, middleName: String? = nil, lastName: String)
    {
        self.firstName = firstName
        self.middleName = middleName
        self.lastName = lastName
    }
    
    let person = Person(firstName: "Foo", lastName: "FooBar")
    

    【讨论】:

    • 哦 wauw.. 但是如果 self.middleName 是可选的,为什么会抛出错误?
    • 查看 Paulw11 的回答中的解释。
    • 是的,这是有道理的。谢谢:D
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-05-02
    • 1970-01-01
    • 1970-01-01
    • 2021-05-18
    • 2017-01-07
    • 1970-01-01
    相关资源
    最近更新 更多