Mapping a Dictionary to an Array of Structs in Swift

Mapping a dictionary to an array of structs in Swift

This gist allowed me solve the problem, with a few modifications:

extension UserDefaults {
func encode<T: Encodable>(_ value: T?, forKey key: String) throws {
switch T.self {
case is Float.Type, is Double.Type, is String.Type, is Int.Type, is Bool.Type:
set(value!, forKey: key)
default:
let data = try value.map(PropertyListEncoder().encode)
let any = data.map { try! PropertyListSerialization.propertyList(from: $0, options: [], format: nil) }

set(any, forKey: key)
}
}

func decode<T: Decodable>(_ type: T.Type, forKey key: String) throws -> T? {
switch T.self {
case is Float.Type, is Double.Type, is String.Type, is Int.Type, is Bool.Type:
return (value(forKey: key) as! T)
default:
let any = object(forKey: key)
let data = any.map { try! PropertyListSerialization.data(fromPropertyList: $0, format: .binary, options: 0) }

return try data.map { try PropertyListDecoder().decode(type, from: $0) }
}
}
}

Using this, I can define the following generic functions:

private func getter<T: Codable>(key: String) -> T {
let result = try! UserDefaults.standard.decode(T.self, forKey: key)
return result!
}

private func setter<T: Codable>(_ newValue: T, forKey key: String) {
try! UserDefaults.standard.encode(newValue, forKey: key)
}

Now I can implement computed getters and setters for all of my properties as such:

var presets: [Preset] {
get {
return getter(presetsKey)
}

set {
setter(newValue, presetsKey)
}
}

It also works for non-array types.

Map array of objects to Dictionary in Swift

Okay map is not a good example of this, because its just same as looping, you can use reduce instead, it took each of your object to combine and turn into single value:

let myDictionary = myArray.reduce([Int: String]()) { (dict, person) -> [Int: String] in
var dict = dict
dict[person.position] = person.name
return dict
}

//[2: "b", 3: "c", 1: "a"]

In Swift 4 or higher please use the below answer for clearer syntax.

Swift Dictionary using subset of Array of Struct

The easiest way to do this is to use reduce(into:) so you can map and group in one step

let suggestionsDict = eventRecords.reduce(into: [:]) {
$0[$1.evType, default: []].append($1.evMainTxt)
}

swift - using .map on struct array

I wanted to filter the entire array just by the first 4 characters of
[i].name

You can achieve this by filtering the array based on the substring value of the name, as follows:

let filteredArray = collectionArray.filter {
$0.name.substring(to: $0.name.index($0.name.startIndex, offsetBy: 4)).lowercased() == "pk00"
// or instead of "pk00", add the first 4 characters you want to compare
}

filteredArray will be filled based on what is the compared string.

Hope this helped.

Map array to be conform with a Model in MVVM structure Swift

Try this:

self.days = (data["days"] as? [[String: Any]] ?? []).map -> StickModel in

Swift: Filter a dictionary key from a struct from an array, which is optional

It's not completely clear to me what you're attempting to do, however, this will filter your cases array to only Test objects that contain non-nil values in the message dictionary:

let nonNil = cases.filter { (test) -> Bool in
return Array(test.message.values).filter({ (value) -> Bool in
return value == nil
}).count <= 0
}

The variable nonNil now contains the Test objects where title is "2" and title is "4".

You could further filter that if you want a [tags:preview] dictionary. Something like this would do that:

let tags = nonNil.map( { $0.message} ).flatMap { $0 }.reduce([String:String]()) { (accumulator, current) -> [String:String] in
guard let key = current.key, let value = current.value else { return accumulator }
var accum = accumulator
accum.updateValue(value, forKey: key)
return accum
}

The tags dictionary now contains: ["tag1": "preview4", "tag2": "preview2"]



Related Topics



Leave a reply



Submit