我在连接字符串时遇到错误:
let likeKey = "like-" + foodPhotoObjects[indexPath.row].objectId
错误
binary operator '+' cannot be applied to operands of type 'String' and 'String?!'
答案 0 :(得分:1)
Swift不进行隐式转换,即使两者属于同一类型且其中一个属于可选类型。
试试这个。
var concatedString = ""
if let foodphoto = foodPhotoObjects[indexPath.row].objectId as? String {
concatedString = "like-" + foodphoto
}
答案 1 :(得分:1)
所以,你有一个隐式包装的可选字符串可选字符串,如下所示:
struct Thing {
let objectId: String?!
}
let foodPhotoObjects: [Thing] = [Thing(objectId: "2")]
对于任何双重包装的可选项,要进入内部对象,您需要打开它两次:
// first unwrap the String?! into a String?
if let outer = foodPhotoObjects[0].objectId,
// then unwrap that String? into a String
inner = outer {
// inner is now a String
println("like-\(inner)")
}
这里的关键是即使外部可选是隐式的(即!
而不是?
),你仍然可以使用if let
展开隐式选项,所以隐含性在做的时候是无关紧要的此
处理此类事物的另一种方法是使用map
而不是if-let:
let concatedString = foodPhotoObjects[indexPath.row].objectId.map {
"like-" + $0
} ?? ""
可选的 map
表示:如果可选项包含值,请使用此函数更改该值并将其作为可选项返回,否则返回nil
。因此,打开String?
并将“喜欢”添加到其中。
??
表示:如果前面的值为nil
,请将其替换为右侧的默认值(空字符串),否则将其打开并返回(即我们刚刚绘制的值。)
现在对于棘手的部分:因为我们调用map
on的值是一个隐式可选项,它将被隐式解包 - 也就是说,map
正在内部调用String?
1}}而不是String?!
。这与if let
的情况不同,nil
在隐式可选的第一个上运行,然后是内部可选。
与所有隐式选项一样,存在实际可能是let explode = Thing(objectId: nil)
// the next line will generate fatal error: unexpectedly
// found nil while unwrapping an Optional value
explode.objectId.map { "like-" + $0 }
的风险,在这种情况下,您的代码会爆炸,如下所示:
// note, ? after objectId
let concatedString = foodPhotoObjects[indexPath.row].objectId?.map {
"like-" + $0
} ?? ""
如果这是一个问题,你可以通过一些可选的链接来防范它:
@import "../bower_components/foundation/scss/foundation";
@import "../bower_components/foundation/scss/normalize";
这个片段可以赢得大多数可选处理技术的奖励,这些技术塞满了一个声明......但它应该做你需要的。