tech_human
tech_human

Reputation: 7110

Swift - Reading different types of values from a dictionary

Presently the code that I have is reading all the values as String. However at times when an integer or decimal values are present, it gets read as nil.

Present code:

let fieldName = String(arr[0])
var res = dict[fieldName.uppercased()] as? String
if res == nil {
   res = dict[fieldName.lowercased()] as? String
}
url = url.replacingOccurrences(of: testString, with: res?.addingPercentEncoding(withAllowedCharacters: allowedCharSet) ?? "")

There are times when "dict[fieldName.uppercased()]" returns value such as 3 or 40.4, but value in my res object is nil since I am expecting a string.

How can I get read different types of values and update the occurrences in my url?

Code that I tried:

let fieldName = String(arr[0])
var res = dict[fieldName.uppercased()] as? AnyObject
if res == nil {
   res = dict[fieldName.lowercased()] as? AnyObject
}
url = url.replacingOccurrences(of: testString, with: res?.addingPercentEncoding(withAllowedCharacters: allowedCharSet) ?? "")

With this I am getting errors while replacing the occurrences since "addingPercentEncoding" only works on String.

So I check the class of res object and if it is not String, I try doing the below, but getting error since res is of type AnyObject and if that's not present, I try to replace it with empty string.

url = url.replacingOccurrences(of: testString, with: res ?? "" as String)

Upvotes: 1

Views: 101

Answers (2)

vadian
vadian

Reputation: 285132

There is a common type of String, Int and Double: CustomStringConvertible

Conditional downcast the value to CustomStringConvertible and get a string with String Interpolation

let fieldName = String(arr[0])
if let stringConvertible = dict[fieldName.uppercased()] as? CustomStringConvertible {
    url = url.replacingOccurrences(of: testString, with: "\(stringConvertible)".addingPercentEncoding(withAllowedCharacters: allowedCharSet
}

Upvotes: 1

Sweeper
Sweeper

Reputation: 272370

You should separate the "get the dictionary value" part and the "convert it to my desired type" part. And you should check the type of the value you got from the dictionary using if let statements.

let value = dict[fieldName.uppercased()] ?? dict[fieldName.lowercased()]

if let string = value as? String {
    url = url.replacingOccurrences(of: testString, with: string.addingPercentEncoding(withAllowedCharacters: allowedCharSet) ?? "")
} else if let double = value as? Double {
    url = url.replacingOccurrences(of: testString, with: "\(double)".addingPercentEncoding(withAllowedCharacters: allowedCharSet) ?? "")
} else if let integer = value as? Int {
    url = url.replacingOccurrences(of: testString, with: "\(integer)".addingPercentEncoding(withAllowedCharacters: allowedCharSet) ?? "")
} else {
    // value is nil, or is none of the types above. You decide what you want to do here
}

Upvotes: 0

Related Questions