Swift 3: Type 'Any' Has No Subscript Members

Type 'Any?' has no subscript members

change this

 let email = result["email"] as? String

into

  guard let resultNew = result as? [String:Any] 

let email = resultNew["email"] as! String

full answer

let parameters = ["fields": "email, first_name, last_name,  picture.type(large)"]
FBSDKGraphRequest(graphPath: "me", parameters: parameters).start { (connection, result, error) in

guard let resultNew = result as? [String:Any]

let email = resultNew["email"] as! String
}

type any? has no subscript members

When you subscript profile with "Addresses", you're getting an Any instance back. Your choice to use Any to fit various types within the same array has caused type erasure to occur. You'll need to cast the result back to its real type, [[String: Any]] so that it knows that the Any instance represents an Array. Then you'll be able to subscript it:

func f() {
let address: [[String : Any]] = [["Address": "someLocation", "City": "ABC","Zip" : 123],["Address": "someLocation", "City": "DEF","Zip" : 456]]
let profile: [String : Any] = ["Name": "Mir", "Age": 10, "Addresses": address]

guard let addresses = profile["Addresses"] as? [[String: Any]] else {
// Either profile["Addresses"] is nil, or it's not a [[String: Any]]
// Handle error here
return
}

print(addresses[0])
}

This is very clunky though, and it's not a very appropriate case to be using Dictionaries in the first place.

In such a situation, where you have dictionaries with a fixed set of keys, structs are a more more appropriate choice. They're strongly typed, so you don't have to do casting up and down from Any, they have better performance, and they're much easier to work with. Try this:

struct Address {
let address: String
let city: String
let zip: Int
}

struct Profile {
let name: String
let age: Int
let addresses: [Address]
}

let addresses = [
Address(
address: "someLocation"
city: "ABC"
zip: 123
),
Address(
address: "someLocation"
city: "DEF"
zip: 456
),
]

let profile = Profile(name: "Mir", age: 10, addresses: addresses)

print(profile.addresses[0]) //much cleaner/easier!

Swift 3 Type 'Any' has no subscript members


let type = (self.data[indexPath.row] as? [String : String])?["Type"]

You need to cast self.data[indexPath.row] to a dictionary.

type 'Any' has no subscript members

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!

Type any has no subscript error in swift 3

I poured over the many questions with duplicate titles and couldn't find one that clearly covered your case, so I'm going to explain what is going on.

Your variable property is clearly declared as type Any, which is a variable that can hold any type. The error message is telling you that you can't use subscripting [] with it. It is clear that you believe that it is a Dictionary with a key that is a String and a value that can be anything. In Swift 3, anything is typed Any. So your property is expected to be [String : Any]. If you cast property to [String : Any], then you will be able to use [] with it.

The first thing you should do is attempt to cast property to [String : Any] and then proceed if that works:

if let property = property as? [String : Any],
let name = property["Name"] as? String,
let latitude = property["Latitude"] as? NSNumber,
let longitude = property["Longitude"] as? NSNumber,
let image = property["Image"] as? String {

// To learn how to read data from plist file, check out our Saving Data
// in iOS Video Tutorial series.

// Code goes here
}

Type 'Any' has no subscript members in Swift 3 Xcode 8

Try this in the parsing section in the middle:

        let parsed = try JSONSerialization.jsonObject(with: data!, options: .allowFragments) as! [String:Any]
let list = parsed["list"] as! [String:Any]?
let resources = list?["resources"] as! [AnyObject]?
let fields = resources?[0] as! [String:Any]?
let resource = fields?["resource"] as! [String:Any]?
let fields2 = resource?["fields"] as! [String:Any]?
let price = fields2?["price"] as! String?

Type 'Any' has no subscript members after updating to Swift 3

In FIRDataSnapshot, value is of type id.

In Swift 3, id is imported as Any.

In the Firebase documentation, it says value can be any of NSDictionary, NSArray, NSNumber, or NSString -- clearly, subscripting doesn't make sense on all of these, especially in Swift. If you know it's an NSDictionary in your case, then you should cast it to that.

Type Any has no subscript members

The problem is exactly what the error message is telling you: to subscript a variable, it needs to be declared as a type which supports subscripting, but you've declared your array as containing Any. And Any, being the most basic type there is, doesn't support subscripting.

Assuming your array contains dictionaries, declare your getMedia function like this instead:

public func getMedia(completion: @escaping ([[String : Any]]) -> ())

Or, if there's a chance that the dictionary might contain non-string keys:

public func getMedia(completion: @escaping ([[AnyHashable : Any]]) -> ())

If the values in the dictionary all have the same type, replace Any with that type as appropriate.



Related Topics



Leave a reply



Submit