Swift结构外部填充

时间:2018-04-08 09:46:50

标签: swift xcode llvm

所以我在swift中有以下结构

typealias float = Float32
typealias Point = float2
typealias Int = UInt32

//This is a struct that is meant to be the elements in an array that is immensly acessable to c
//CAREFUL this is LIKELY mirrored in a different thing
public struct Info {
    var position:Point = Point(x: 0, y: 0)
    var strength:float = 1
    var altitude:float = 3.141592 / 2.0
    var azmuth:Point = Point(x: 0, y: 0)
    var state:Int = 0
}

此结构存储在使用Array(repeating: ...

分配的数组中

每一帧我都将指向该数组的指针传递到我的c ++代码中,我在这里有一个镜像结构

struct Info {
    float positionX;
    float positionY;
    float strength;
    float altitude;
    float azmuthX;
    float azmuthY;
    int state;
    float pad; //WHy???
}; 

现在注意它在那里的额外的浮点“pad”,因为当我去读取第一个元素以外的元素时,没有它在结构声明中,数据被一个float的大小偏移(事物将被移动一个字段结束)。

为什么c ++结构上的pad字段是必需的? Swift中额外填充的额外浮动或原因是什么?

1 个答案:

答案 0 :(得分:2)

ConfigFileReader.Java17: FileInputStream fis = new FileInputStream(propertyFilePath); EndtoEndTest.java32:cnffilered = new ConfigFileReader(); 是C类型float2的Swift映射,它是 在simd_float2中定义为

<simd/vector_types.h

关键点是

  

此类型的对齐方式大于float

的对齐方式

您可以使用

验证
/*! @abstract A vector of two 32-bit floating-point numbers.
 *  @description In C++ and Metal, this type is also available as
 *  simd::float2. The alignment of this type is greater than the alignment
 *  of float; if you need to operate on data buffers that may not be
 *  suitably aligned, you should access them using simd_packed_float2
 *  instead.                                                                  */
typedef __attribute__((__ext_vector_type__(2))) float simd_float2;

这会导致Swift类型print(MemoryLayout<float>.alignment) // 4 print(MemoryLayout<float2>.alignment) // 8 对齐为8,其步幅(即偏移量) 以字节为单位存储在数组中的连续Info元素之间的字节数为32。

Info

另一方面,C类型print(MemoryLayout<Info>.alignment) // 8 print(MemoryLayout<Info>.stride) // 32 只有struct Infofloat 成员,都具有4个字节的对齐。没有 final int成员,数组中此类型的连续元素之间的偏移量为28个字节,而不是32个。

这解释了差异。你实际应该做的是定义 仅限C类型,并将该定义导入Swift。这是 保证保留内存布局的唯一方法, 正如Apple的Joe Groff所写 multiprocessing

  

如果您依赖于特定的布局,则应该在C中定义结构并将其导入到Swift中。