UnsafeMutablePointer到期望的参数类型UnsafeMutablePointer< _>在Swift 3中

时间:2016-10-12 17:25:43

标签: swift macos cocoa swift3 receigen

main.swift文件中,我们调用了收据检查系统(由Receigen生成)。在Swift 2中,main.swift读取:

startup(Process.argc, UnsafeMutablePointer<UnsafePointer<Int8>>(Process.unsafeArgv))

升级到Swift 3之后,我已经达到了:

startup(CommandLine.argc, UnsafeMutablePointer<UnsafePointer<Int8>>(CommandLine.unsafeArgv))

显示错误:

  

无法转换类型的值   UnsafeMutablePointer<UnsafeMutablePointer<Int8>?>(又名   UnsafeMutablePointer<Optional<UnsafeMutablePointer<Int8>>>)   预期参数类型UnsafeMutablePointer<_>

更新:使用linked question,使其显示为:

startup(CommandLine.argc, UnsafeMutableRawPointer(CommandLine.unsafeArgv)
    .bindMemory(
        to: UnsafeMutablePointer<Int8>.self,
        capacity: Int(CommandLine.argc)))

产地:

  

无法将UnsafeMutablePointer<Int8>.Type类型的值转换为   期望参数类型UnsafePointer<Int8>?.Type(又名   Optional<UnsafePointer<Int8>>.Type

编译器指的是to:UnsafeMutablePointer

启动标题如下:

int startup(int argc, const char * argv[]);

如何在main.swift中成功将变量传递给启动?

1 个答案:

答案 0 :(得分:7)

基本上,这是此处讨论的问题的变体:

Xcode 8 beta 6: main.swift won't compile

问题是,CommandLine.unsafeArgv的类型与C函数预期的类型之间存在阻抗不匹配。并且你不能仅仅通过从一个可变指针类型强制转换到另一个指针类型来抛弃这种不匹配。相反,您必须通过调用bindMemory将其从一种类型转换为另一种类型。并且要求Optional<UnsafePointer<Int8>>.Type的错误消息告诉您要转向的类型:

    startup(
        CommandLine.argc,
        UnsafeMutableRawPointer(CommandLine.unsafeArgv)
            .bindMemory(
                to: Optional<UnsafePointer<Int8>>.self,
                capacity: Int(CommandLine.argc))
    )

那应该允许你编译。在我的机器上使用startup存根进行测试,它实际运行。但无论它是否会在你的机器上运行,以及它是否安全,都是有人猜的!这件事无可否认令人抓狂......

编辑在iOS 12 / Xcode 10中修复了CommandLine.unsafeArgv的问题,因此可能也解决了这个问题。