web-dev-qa-db-ja.com

Swiftクラス/構造体データを辞書に変換できますか?

例えば:

class Test {
    var name: String;
    var age: Int;
    var height: Double;
    func convertToDict() -> [String: AnyObject] { ..... }
}

let test = Test();
test.name = "Alex";
test.age = 30;
test.height = 170;

let dict = test.convertToDict();

dictにはコンテンツがあります:

{"name": "Alex", "age": 30, height: 170}

これはSwiftで可能ですか?

そして、おそらく次のようなものを使用して、辞書のようなクラスにアクセスできますか?

test.value(forKey: "name");

またはそのような何か?

ありがとう。

12
Chen Li Yong

計算プロパティをstructに追加するだけで、値を含むDictionaryを返すことができます。 Swiftネイティブ辞書タイプにはvalue(forKey:)というメソッドがありません。DictionaryNSDictionaryにキャストする必要があります。

struct Test {
    let name: String
    let age: Int
    let height: Double
    var dictionary: [String: Any] {
        return ["name": name,
                "age": age,
                "height": height]
    }
    var nsDictionary: NSDictionary {
        return dictionary as NSDictionary
    }
}

@ColGraffによって投稿されたリンクされた回答で提案されているようにEncodableプロトコルを拡張して、すべてのEncodable構造体にユニバーサルにすることもできます。

struct JSON {
    static let encoder = JSONEncoder()
}
extension Encodable {
    subscript(key: String) -> Any? {
        return dictionary[key]
    }
    var dictionary: [String: Any] {
        return (try? JSONSerialization.jsonObject(with: JSON.encoder.encode(self))) as? [String: Any] ?? [:]
    }
}

struct Test: Codable {
    let name: String
    let age: Int
    let height: Double
}

let test = Test(name: "Alex", age: 30, height: 170)
test["name"]    // Alex
test["age"]     // 30
test["height"]  // 170
32
Leo Dabus

このようなReflectionとMirrorを使用して、より動的にし、プロパティを忘れないようにすることができます。

struct Person {
  var name:String
  var position:Int
  var good : Bool
  var car : String

  var asDictionary : [String:Any] {
    let mirror = Mirror(reflecting: self)
    let dict = Dictionary(uniqueKeysWithValues: mirror.children.lazy.map({ (label:String?,value:Any) -> (String,Any)? in
      guard label != nil else { return nil }
      return (label!,value)
    }).compactMap{ $0 })
    return dict
  }
}


let p1 = Person(name: "Ryan", position: 2, good : true, car:"Ford")
print(p1.asDictionary)

["name": "Ryan"、 "position":2、 "good":true、 "car": "Ford"]

8
Ryan Heitner