Swift 3中如何使用getopt处理命令行参数?

3

我正在尝试在Swift 3中使用getopt处理命令行参数。我参考了Michele Dall'Agata在stackoverflow的贡献

let pattern = "abc:"
var buffer = Array( pattern.utf8 ).map { Int8($0) }

当我使用这段代码时:
let option = Int( getopt( CommandLine.argc, CommandLine.arguments, buffer ) )

我遇到了这个错误:

无法将类型为 '[String]' 的值转换为预期的参数类型 'UnsafePointer<UnsafeMutablePointer<Int8>?>!'

我正在尝试使用CommandLine.arguments作为argv。有谁知道getopt的第二个参数的正确语法吗?提前感谢!

请复制实际错误。 - Alexander
这就是Xcode中CommandLine.arguments上方显示的确切错误。 - Dribbler
'UnsafePointer?>!'这一部分也要翻译吗? - Alexander
我回到控制台前会再三确认,但我相信是的。 - Dribbler
2
@Alexander 这是一个 Markdown 格式错误;我已经修复了。 - jtbandes
2个回答

8

@Hamish已经回答了这个问题,并解释了如何在Swift中传递CommandLine.unsafeArgvgetopt()(以及为什么要这样做)。

下面是一个完整的自包含示例,展示了如何在Swift 3中实现典型的getopt循环:

var aFlag = false
var bFlag = false
var cValue: String?

while case let option = getopt(CommandLine.argc, CommandLine.unsafeArgv, "abc:"), option != -1 {
    switch UnicodeScalar(CUnsignedChar(option)) {
    case "a":
        aFlag = true
    case "b":
        bFlag = true
    case "c":
        cValue = String(cString: optarg)
    default:
        fatalError("Unknown option")
    }
}

print(aFlag, bFlag, cValue ?? "?")

备注:

  • You can pass a Swift string (here: "abc:") directly to a C function expecting a (constant) C string, the compiler will automatically generate a temporary UTF-8 representation.
  • getopt() return either -1 (if the argument list is exhausted) or an unsigned char converted to an int. Therefore it is safe to convert the return value to CUnsignedChar (which is UInt8 in Swift).
  • while is used (abused?) with pattern matching plus an additional boolean condition to implement the typical C pattern

    while ((option = getopt(argc, argv, "abc:")) != -1) { ... }
    

    in Swift.


6

CommandLine.arguments会返回一个友好的Swift [String],其中包含传递的参数 - 但是您希望将参数直接发送回C。因此,您可以使用CommandLine.unsafeArgv替代,这将为您提供传递给程序的argv的实际原始值。

let option = Int( getopt( CommandLine.argc, CommandLine.unsafeArgv, buffer ) )

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接