c语言 - 数组元素取消引用和寻址 - &buffer[index] - 在 Swift 中有效吗?



我正在编写一个Swift应用程序,我需要使用C函数从套接字进行一些网络缓冲。Swift通过桥接头导入这些函数,它们需要一个缓冲区指针参数。

这两个函数有效地:

read(Socket s, void *buf, int num);
write(Socket s, const void *buf, int num);

Swift编译器指出,如果这些函数需要一个UnsafePointer<Void>。我有一些[UInt8]类型保存我的可写数据和接受我的可读数据。Swift编译器并没有抱怨我所写的东西,但是我相信下面的代码并没有按照我在C语法中期望的那样做。

这是我的read循环:

var index: Int32 = 0    
while index < length {
    var toRead = length - index
    if toRead > bufferSize {
        toRead = bufferSize
    }
    // Read into my buffer ([Int8]), starting at element `hasRead`
    let justRead: Int32 = read(s, &buffer[Int(index)], toRead)
    index += justRead
}

和我的write循环:

var index: Int32 = 0
while index < length {
    var toWrite: Int32 = length - index
    if toWrite > bufferSize {
        toWrite = bufferSize
    }
    // Write from my buffer ([Int8]), starting at element `index`
    let wrote = write(s, &buffer[Int(index)], toWrite)
    index += wrote
}

我的问题是:在这种情况下,&buffer[Int(index)]是传递(可变)数组的正确方法吗?(也就是说,它正在做我期望C用这种语法做的事情-获取数组字节的第索引元素的地址)。如果不是,我如何恰当地将[UInt8]传递给桥接的C函数?

我建议谨慎使用&buffer[Int(index)]。目前还不清楚从医生那里能保证什么。当然,它可以用来修改数组的单个元素,但我认为你不应该依赖于指针运算(所以你不应该把它传递给这样的函数)。

但是,您可以/应该使用的是withUnsafeMutableBufferPointer()(目前显然不在文档中)(或不可变版本)。这保证使用一个UnsafeMutableBufferPointer来调用所提供的闭包,该闭包指向可用于读取和写入数组的连续存储。您可能会想使用它的baseAddress .

(还要注意Swift除了Array之外还有一个连续数组,它的存储保证是连续的,所以你可能会看到比Array更好的性能,因为你知道你无论如何都会要求它提供一个连续的缓冲区。)但是不要在这里对性能做太多的假设——它没有很好的文档记录!我怀疑你需要在实践中使用连续数组

你可以:

read(s, &buffer + Int(index), toRead)

我认为,&buffer[Int(index)]是不安全的,正如在这个QA

最新更新