无法强制解包非可选类型的值 'AnyObject'
Cannot force unwrap value of non-optional type 'AnyObject'
我已将我的 iOS 项目从 swift 2.x 转换为 swift 3.x
我的代码中现在有 50 多个错误。最常见的之一是这个 "Cannot force unwrap value of non-optional type 'AnyObject'"
这是部分代码:
第 let documentURL = JSON[eachOne]["media"]!![eachMedia]["media_url"]!
行产生了错误
我该如何解决这个问题?谢谢!
if let JSON = response.result.value as? [[String: AnyObject]]{
//print("JSON: \(JSON)")
myDefaultValues.userDefaults.setValue(JSON, forKey: "JSON")
for eachOne in 0 ..< (JSON as AnyObject).count{
// print("Cover: \(JSON[eachOne]["cover"])")
//Download all Covers
let documentURL = JSON[eachOne]["cover"]!
let pathus = URL(string: documentURL as! String)
if pathus != nil {
HttpDownloader.loadFileSync(pathus!, completion:{(path:String, error:NSError!) in
})
}
//Download all Media Files
if JSON[eachOne]["media"] != nil{
//print(JSON[eachOne]["media"]!)
//print(JSON[eachOne]["media"]!!.count)
let thisMediaView = JSON[eachOne]["media"]!.count
for eachMedia in 0 ..< thisMediaView!{
//print(JSON[eachOne]["media"]!![eachMedia]["media_url"])
**let documentURL = JSON[eachOne]["media"]!![eachMedia]["media_url"]!**
let pathus = URL(string: documentURL as! String)
if pathus != nil {
HttpDownloader.loadFileSync(pathus!, completion:{(path:String, error:NSError!) in
})
}
}
}
}
}
首先,代码中的以下行生成一个 Int,而不是一个数组:
let thisMediaView = JSON[eachOne]["media"]!.count
其次,您可以强制展开所有值,但这会带来很多风险。你不应该强行解包,除非......不等,只是不要强行解包。
你这里的行对你 JSON 中的值类型做了很多假设,但没有实际检查。
let documentURL = JSON[eachOne]["media"]!![eachMedia]["media_url"]!
为了更安全,更能表达,试着写成这样:
if let value = JSON[eachOne] as? [String: Any],
let anotherValue = JSON[value] as? [String: Any],
...etc,
let documentURL = anotherValue["media_url"] as? String {
// do something with the values
} else {
// handle unexpected value or ignore
}
作为初学者 Swift 程序员,您应该假装 !
强制解包运算符不存在。我称之为 "crash if nil" 运算符。相反,您应该使用 if let
或 guard let
可选绑定。您将 JSON 对象转换为字典数组,因此直接使用该数组:
for anObject in JSON {
guard let mediaArray = anObject["media"] as [[String: Any]] else
{
return
}
for aMediaObject in mediaArray {
guard let aMediaDict = aMediaObject as? [String: Any],
let documentURLString = aMediaDict["media_url"] as? String,
let url = URL(string: documentURLString ) else
{
return
}
//The code below is extracted from your question. It has multiple
//issues, like using force-unwrap, and the fact that it appears to be
//a synchronous network call?
HttpDownloader.loadFileSync(pathus!,
completion:{(path:String, error:NSError!) in {
}
}
}
该代码可能并不完美,但它应该能给您思路。
我已将我的 iOS 项目从 swift 2.x 转换为 swift 3.x 我的代码中现在有 50 多个错误。最常见的之一是这个 "Cannot force unwrap value of non-optional type 'AnyObject'"
这是部分代码:
第 let documentURL = JSON[eachOne]["media"]!![eachMedia]["media_url"]!
行产生了错误
我该如何解决这个问题?谢谢!
if let JSON = response.result.value as? [[String: AnyObject]]{
//print("JSON: \(JSON)")
myDefaultValues.userDefaults.setValue(JSON, forKey: "JSON")
for eachOne in 0 ..< (JSON as AnyObject).count{
// print("Cover: \(JSON[eachOne]["cover"])")
//Download all Covers
let documentURL = JSON[eachOne]["cover"]!
let pathus = URL(string: documentURL as! String)
if pathus != nil {
HttpDownloader.loadFileSync(pathus!, completion:{(path:String, error:NSError!) in
})
}
//Download all Media Files
if JSON[eachOne]["media"] != nil{
//print(JSON[eachOne]["media"]!)
//print(JSON[eachOne]["media"]!!.count)
let thisMediaView = JSON[eachOne]["media"]!.count
for eachMedia in 0 ..< thisMediaView!{
//print(JSON[eachOne]["media"]!![eachMedia]["media_url"])
**let documentURL = JSON[eachOne]["media"]!![eachMedia]["media_url"]!**
let pathus = URL(string: documentURL as! String)
if pathus != nil {
HttpDownloader.loadFileSync(pathus!, completion:{(path:String, error:NSError!) in
})
}
}
}
}
}
首先,代码中的以下行生成一个 Int,而不是一个数组:
let thisMediaView = JSON[eachOne]["media"]!.count
其次,您可以强制展开所有值,但这会带来很多风险。你不应该强行解包,除非......不等,只是不要强行解包。
你这里的行对你 JSON 中的值类型做了很多假设,但没有实际检查。
let documentURL = JSON[eachOne]["media"]!![eachMedia]["media_url"]!
为了更安全,更能表达,试着写成这样:
if let value = JSON[eachOne] as? [String: Any],
let anotherValue = JSON[value] as? [String: Any],
...etc,
let documentURL = anotherValue["media_url"] as? String {
// do something with the values
} else {
// handle unexpected value or ignore
}
作为初学者 Swift 程序员,您应该假装 !
强制解包运算符不存在。我称之为 "crash if nil" 运算符。相反,您应该使用 if let
或 guard let
可选绑定。您将 JSON 对象转换为字典数组,因此直接使用该数组:
for anObject in JSON {
guard let mediaArray = anObject["media"] as [[String: Any]] else
{
return
}
for aMediaObject in mediaArray {
guard let aMediaDict = aMediaObject as? [String: Any],
let documentURLString = aMediaDict["media_url"] as? String,
let url = URL(string: documentURLString ) else
{
return
}
//The code below is extracted from your question. It has multiple
//issues, like using force-unwrap, and the fact that it appears to be
//a synchronous network call?
HttpDownloader.loadFileSync(pathus!,
completion:{(path:String, error:NSError!) in {
}
}
}
该代码可能并不完美,但它应该能给您思路。