使用Swift中的sysctlbyname()

bde*_*ham 17 cocoa-touch swift

我正在使用此Gist中的代码来确定iPhone5,1运行我的应用程序的iOS设备(例如):

- (NSString *)platform
{
    size_t size;
    sysctlbyname("hw.machine", NULL, &size, NULL, 0);
    char *machine = malloc(size);
    sysctlbyname("hw.machine", machine, &size, NULL, 0);
    NSString *platform = [NSString stringWithUTF8String:machine];
    free(machine);
    return platform;
}
Run Code Online (Sandbox Code Playgroud)

Swift文档表明C数据类型得到了很好的支持,但它没有提到C函数的任何内容.是否有一种纯粹的Swift方法来检索机器标识符,或者我是否必须桥接到Objective-C?

Mar*_*n R 45

您可以在Swift中执行相同的操作(为简洁起见,省略了错误检查):

func platform() -> String {
    var size : Int = 0 // as Ben Stahl noticed in his answer
    sysctlbyname("hw.machine", nil, &size, nil, 0)
    var machine = [CChar](count: size, repeatedValue: 0)
    sysctlbyname("hw.machine", &machine, &size, nil, 0)
    return String.fromCString(machine)!
}
Run Code Online (Sandbox Code Playgroud)

Swift 3更新:

func platform() -> String {
    var size = 0
    sysctlbyname("hw.machine", nil, &size, nil, 0)
    var machine = [CChar](repeating: 0,  count: size)
    sysctlbyname("hw.machine", &machine, &size, nil, 0)
    return String(cString: machine)
}
Run Code Online (Sandbox Code Playgroud)

  • 好吧,我会被诅咒的。我想我应该先尝试这个。谢谢! (2认同)

Ben*_*ahl 15

从Swift 1.2(Xcode 6.3 beta-2)开始,@ MartinR的代码需要稍微修改一下.sysctlbyname需要第一个参数的CChar数组(即C字符串),以及"size"参数的Int(而不是Uint).

func platformModelString() -> String? {
    if let key = "hw.machine".cString(using: String.Encoding.utf8) {
        var size: Int = 0
        sysctlbyname(key, nil, &size, nil, 0)
        var machine = [CChar](repeating: 0, count: Int(size))
        sysctlbyname(key, &machine, &size, nil, 0)
        return String(cString: machine)
    }
    return nil
}
Run Code Online (Sandbox Code Playgroud)

编辑:更新2017-01-04为Swift 3语法