我们可以在Swift上重用struct吗?还是有其他办法吗?

时间:2018-05-31 12:19:01

标签: ios json swift decodable

所以我有一个用户JSON结构,如下所示:

- results: {
    meta: {}
    users: []
  },
- status:

我想让用户知道我实现的User模型以获取JSON是这样的:

struct Response: Decodable {

    let results: Result
    let status: Int
}

struct Result: Decodable {

    let meta: Meta
    let users: [User]
}

struct Meta: Decodable {

    let total_data: Int
    let total_page: Int
}

struct User: Decodable {

    let avatar_url: String
    let created_at: String
    let updated_at: String
    let email: String
    let id: Int
    let name: String
    let username: String
}

它正在工作,但是当我有另一个结构相似的JSON时,就像这样说

- results: {
        meta: {}
        rooms: []
      },
    - status:

当我创建Room模型时,其上有另一个struct Response,它会导致错误,因为它是重复的声明。

是否有可能在Swift中重用struct?或者有什么方便的方法吗?

由于

4 个答案:

答案 0 :(得分:8)

您可以使用泛型。

struct Response<T: Decodable>: Decodable {
    let results: Result<T>
    let status: Int
}

struct Result<T: Decodable>: Decodable {
    let meta: Meta
    let objects: [T]
}

struct Meta: Decodable {    
    let total_data: Int
    let total_page: Int
}

struct User: Decodable {
    let avatar_url: String
    let created_at: String
    let updated_at: String
    let email: String
    let id: Int
    let name: String
    let username: String
}

let userResponse: Response<User>?

答案 1 :(得分:2)

您可以尝试以下列方式使用泛型:

struct Result: Decodable {
    let something: String
}

let decoder = JSONDecoder()
let data = "{\"status\":123,\"results\":{\"something\":\"hi\"}}".data(using: .utf8)!
let value = try! decoder.decode(Response<Result>.self, from: data) // will be of type Response<Result>

然后通过以下方式使用该结构:

{{1}}

答案 2 :(得分:1)

您有一个选择是重复使用MetaStatus 如果你使用sm

对于用户您可以替换名称

struct UserResult: Decodable {

    let meta: Meta
    let users: [User]
}

struct UserResponse: Decodable {

    let results: UserResult
    let status: Int
}

和房间

struct RoomResult: Decodable {

    let meta: Meta
    let users: [Room]
}

struct RoomResponse: Decodable {

    let results: RoomResult
    let status: Int
}

答案 3 :(得分:1)

根据您的需要,您可以使用泛型来组成整个结构。

从数据模型开始

struct User: Decodable {
    let avatar_url: String
    let created_at: String
    let updated_at: String
    let email: String
    let id: Int
    let name: String
    let username: String
}

struct Room: Decodable {
    let id: Int
    let name: String
}

目标是获得好的组合类型。

typealias UserResponse = Response<Result<User, Meta>>
typealias RoomResponse = Response<Result<Room, Meta>>

要从

构建的泛型类型
struct Response<ResultType: Decodable>: Decodable {
    let results: ResultType
    let status: Int
}

struct Result<ItemType: Decodable, MetaType: Decodable>: Decodable {
    let meta: MetaType
    let items: [ItemType]
}

即使Meta也是合成的一部分。

struct Meta: Decodable {
    let total_data: Int
    let total_page: Int
}

现在假设我们需要Meta响应的自定义Room

struct PagedMeta: Decodable {
    let current_page: Int
    let page_count: Int
}

这是新类型

typealias RoomPagedResponse = Response<Result<Room, PagedMeta>>