【问题标题】:Convert my type to expected argument type将我的类型转换为预期的参数类型
【发布时间】:2021-05-14 13:01:43
【问题描述】:

我正在使用 Apollo Client 在 Xcode 中自动生成 graphql 类型和查询,但遇到了一个我不知道如何最好地解决的问题。 TLDR 是如何允许将一个结构用作接受具有相同结构的另一种类型的函数的参数?

Apollo 为我生成了一个名为“SizeInput”的结构,如下所示:

struct SizeInput: GraphQLMapConvertible {
  public var graphQLMap: GraphQLMap
  public init(cm: Double) {
    graphQLMap = ["cm": cm]
  }
  public var cm: Double {
    get {
      return graphQLMap["cm"] as! Double
    }
    set {
      graphQLMap.updateValue(newValue, forKey: "cm")
    }
  }
}

(顺便说一句 - GraphQLMap[String : JSONEncodable?] 的类型别名)

我创建了一个 Size 结构用于我的代码。我不想在我的代码中使用SizeInput 将后端与我的应用代码分开,这样如果后端或应用发生变化,事情就不会中断。

struct Size {
  let cm: Double
}

我需要运行一个以 SizeInput 作为参数的 apollo 查询,我想从选择器填充的 Size 变量中填充该参数。虽然我知道我可以从Size 创建一个新的SizeInput,但我很想将Size 传递到查询中,因为它们本质上是相同的,只是两种不同的类型。截至目前,XCode 明显在抱怨Cannot convert value of type 'Size' to expected argument type 'SizeInput'

关键是我不能(不想)更改 Apollo 函数,因为它是自动生成的。所以我理想的解决方案是以某种方式将Size 类型转换为SizeInput,但是如果我只是尝试执行let sizeInput = size as? SizeInput,其中sizeSize,XCode 就会抱怨。

假设我不能修改接受参数的函数并且我不能修改 SizeInput 因为两者都是自动生成的,我该如何修改 Size 以便它可以用作 SizeInput 参数?

【问题讨论】:

  • 您能否扩展struct Size 使用返回您需要的SizeInput 类型的函数,然后在需要SizeInput 的调用点调用该函数?
  • 如果这最终成为最佳解决方案,我可以。我希望有一种干净的方式能够将Size 用作SizeInput

标签: swift xcode apollo


【解决方案1】:

根据您的帖子,SizeSizeInput 是两种不同的类型,因此不能按照您的想法进行类型别名。

Swift's Declarations reference 说以下关于typealias

类型别名声明将现有类型的命名别名引入您的程序。 [...]声明类型别名后,可以在程序中的任何地方使用别名名称代替现有类型。 [...] 类型别名不会创建新类型;它们只是允许名称引用现有类型。

...但这不是你想要的。 SizeSizeInput 在合同上相似,因为它们具有 cm: Double 属性,但在底层结构上不同,不能互换使用。

无论您选择何种解决方案,您都需要做出一些权衡。我至少看到以下选项。

  • 您可以编写一个位于您的代码生成 GraphQL 内容之上的层,该层提供您想要的接口(即采用Size)并使用它。然后将您的Size 翻译成SizeInput。可以使用 Codegen。
  • 您可以在Size 类型本身上提供SizeSizeInput 的某种类型级函数,然后在您的GraphQL 调用站点使用它。 Codegen 也可以在这里使用。
extension Size {
   func asSizeInput() -> SizeInput {
        return SizeInput(cm: cm)
    }
}
  • 您也可以在调用站点将您的Size 实例的cm 属性传递给SizeInput 的构造函数,这样您就不会编写任何额外的代码。这是一些伪代码:
let size = Size(cm: 100)
let query = SizeInputGraphQLQuery(sizeInput: size.cm)

对于我的 $,我会选择编写尽可能少的额外代码。

YMMV

【讨论】:

  • 这是我怀疑但想确认的。谢谢!
猜你喜欢
  • 2021-04-29
  • 2016-07-27
  • 2016-07-02
  • 1970-01-01
  • 2016-03-21
  • 2021-02-02
  • 2020-03-01
  • 2016-08-01
  • 2017-02-07
相关资源
最近更新 更多