【问题标题】:How to Unwrap a Modal class object in Swift 3如何在 Swift 3 中打开模态类对象
【发布时间】:2017-04-21 05:29:12
【问题描述】:

模型类:

class CountryModel: NSObject {

    var name:NSString!

    var countryId:NSString!

    init(name: NSString, countryId: NSString) {
        self.name = name
        self.countryId = countryId
    }

}

视图控制器:

var nameArr = [CountryModel]() // Model Class object

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {

        var cell = UITableViewCell()

        cell = tableView.dequeueReusableCell(withIdentifier: "cell")!

        let arr = nameArr[indexPath.row] // How to do if let here

        let str:String? = "\(arr.countryId) \(arr.name)"

        if let sstr = str{
            cell.textLabel?.text = sstr
        }

        return cell

    }

如果我尝试解包 nameArr[indexPath.row] 给出错误,应该如何解包,因为输出是可选的,条件绑定的初始化程序必须具有可选类型,而不是“国家模式”

它工作正常我没有将 arr.countryId 与 arr.name 连接

【问题讨论】:

  • 在 modelClass 中使用 String 而不是 NSString 并且 CountryModal 不是可选的 .. 它会给你那个警告。不需要在那里检查可选
  • @EICaptainv2.0 谢谢先生,但是按照你说的做之后它给出了一个可选的“结果这里”,之前有两个可选的(可选的“这里的值”)

标签: ios swift3 optional unwrap forced-unwrapping


【解决方案1】:

这很好用

        var nameArr = [CountryModal]()
        nameArr.append(CountryModal.init(name: "harshal", countryId: "india"))
        nameArr.append(CountryModal.init(name: "james", countryId: "australia"))

        let arr = nameArr[0]
        let str:String? = "\(arr.countryId!) \(arr.name!)" 
        if let sstr = str{
           print(sstr)
        }

        let arr2 = nameArr[1]
        let str2:String? = "\(arr2.countryId!) \(arr2.name!)"

        if let sstr2 = str2{
            print(sstr2)
        }

【讨论】:

  • 感谢数组中的数据来自 JSON,现在 arr2.name 仍然是可选的,它说 Afghanistan Optional(1)
  • 好的,我从 JSON 中得到了一个 Int,所以在初始化器中我取了一个 Int 类型,然后转换为字符串,它工作了,谢谢
  • 这是一个很奇怪的例子,因为你注解了一个可选的字符串常量(String?)但是却分配了一个100%的非可选值,所以可选绑定是没有意义的。另一方面,如果countryIdnamenil,则代码会崩溃。
【解决方案2】:

你可以试试这个库https://github.com/T-Pham/NoOptionalInterpolation。它正是这样做的 import NoOptionalInterpolation

let n: Int? = 1
let t: String? = nil
let s: String? = "string1"
let o: String?? = "string2"

let i = "\(n) \(t) \(s) \(o)"
print(i) // 1  string1 string2

NoOptionalInterpolation 摆脱了 Swift 字符串插值中的“Optional(...)”和“nil”。该库确保您设置的文本永远不会包含烦人的附加“Optional(...)”。您还可以在需要时恢复到默认行为。

另外,请注意这不会影响打印功能。因此,print(o)(与上面示例中的 print("(o)")相反,o 仍然会打印出 Optional(Optional("string2"))

【讨论】:

  • 有趣,但请多解释一下,那里的线条是什么意思
  • 我已经更新了帖子,我想这会对你有所帮助。这是一个非常简单和轻量级的库。如果您查看实现,您将很容易理解。它具有 Unwrappable 协议和 Optional 扩展,可提取可选值。
【解决方案3】:

尽可能避免强制解包。即使用“!”。每当您看到 ! 时,请尝试将其视为代码异味。

对于 json 解析,您无法确定 countryId 和 name 的值是否存在。因此,将它们保留为可选项并在以后优雅地尝试打开它们是有意义的。

class CountryModel {

var name: String?
var countryId: String?

init(name: String?, countryId: String?) {
    self.name = name
    self.countryId = countryId
}

}

var nameArr = [CountryModel]()

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {

guard let cell = tableView.dequeueReusableCell(withIdentifier: "cell") else {
    fatalError("cell should always be initialised")
}

var str: String?

let arr = nameArr[indexPath.row] // How to do if let here

if let countryId = arr.countryId, let name = arr.name {
    str = "\(countryId) \(name)"
}

if let unwrappedString = str {
    cell.textLabel?.text = unwrappedString
}

return cell
}

奖金: 您可以使用Object Mapper 库大大简化您的 json 解析。它简化了很多解析逻辑。

【讨论】:

    猜你喜欢
    • 2017-02-07
    • 1970-01-01
    • 1970-01-01
    • 2017-03-16
    • 1970-01-01
    • 2017-11-09
    • 1970-01-01
    • 1970-01-01
    • 2015-10-28
    相关资源
    最近更新 更多