type 'Any' has no subscript members

2020-02-13 06:26发布

let employerName = snapshot.value! ["employerName"] as! String
let employerImage = snapshot.value! ["employerImage"] as! String
let uid = snapshot.value! ["uid"] as! String

I reviewed previous posts but cannot seem to find a way to solve this problem. All three lines of code give the "type 'Any' has no subscript members" error. Fairly new to this so any help is appreciated.

标签: swift swift3
2条回答
不美不萌又怎样
2楼-- · 2020-02-13 07:11

snapshot.value has a type of Any. A subscript is a special kind of function that uses the syntax of enclosing a value in braces. This subscript function is implemented by Dictionary.

So what is happening here is that YOU as the developer know that snapshot.value is a Dictionary, but the compiler doesn't. It won't let you call the subscript function because you are trying to call it on a value of type Any and Any does not implement subscript. In order to do this, you have to tell the compiler that your snapshot.value is actually a Dictionary. Further more Dictionary lets you use the subscript function with values of whatever type the Dictionary's keys are. So you need to tell it you have a Dictionary with keys as String(AKA [String: Any]). Going even further than that, in your case, you seem to know that all of the values in your Dictionary are String as well, so instead of casting each value after you subscript it to String using as! String, if you just tell it that your Dictionary has keys and values that are both String types (AKA [String: String]), then you will be able to subscript to access the values and the compiler will know the values are String also!

guard let snapshotDict = snapshot.value as? [String: String] else {
    // Do something to handle the error 
    // if your snapshot.value isn't the type you thought it was going to be. 
}

let employerName = snapshotDict["employerName"]
let employerImage = snapshotDict["employerImage"]
let uid = snapshotDict["fid"]

And there you have it!

查看更多
叛逆
3楼-- · 2020-02-13 07:16

Since you want to treat snapshot.value as an unwrapped dictionary, try casting to one and, if it succeeds, use that dictionary.

Consider something like:

func findElements(candidate: Any) {
    if let dict: [String : String] = candidate as? Dictionary {
        print(dict["employerName"])
        print(dict["employerImage"])
        print(dict["uid"])
    }
}

// Fake call    
let snapshotValue = ["employerName" : "name", "employerImage" : "image", "uid" : "345"]
findElements(snapshotValue)
查看更多
登录 后发表回答