我们可以在 Swift 上重用结构吗?或者还有其他办法吗?

Can we reuse struct on Swift? Or is there any other way?

所以我有一个用户 JSON 结构是这样的:

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

我想获取用户,所以我为获取 JSON 而实施的 User 模型如下所示:

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 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>?

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

struct Response<ResultType> : Decodable where ResultType : Decodable {
    let results: ResultType
    let status: Int
}

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

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>

您有一个选择是重复使用 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
}

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

从您的数据模型开始

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>>