Struct 为什么有些结构类型允许我们设置只能是某个值的成员?

Struct 为什么有些结构类型允许我们设置只能是某个值的成员?,struct,types,vulkan,Struct,Types,Vulkan,我正在阅读一些vulkan结构类型,这是许多示例之一,但我将使用的是vkInstanceCreateInfo。文件规定: VkInstanceCreateInfo结构定义为: 然后在下面我们看到的选项中: sType就是这种结构的类型 sType必须是VK\u结构\u类型\u实例\u创建\u信息 如果我们没有任何选项,为什么这个参数不只是在创建类型时隐式设置的呢 注意:我意识到这不是vulkan API特有的东西 更新:我不是专门谈论vulkan,而是所有只能是特定类型的参数。该设计允许将结构链

我正在阅读一些vulkan结构类型,这是许多示例之一,但我将使用的是vkInstanceCreateInfo。文件规定:

VkInstanceCreateInfo结构定义为:

然后在下面我们看到的选项中:

sType就是这种结构的类型

sType必须是VK\u结构\u类型\u实例\u创建\u信息

如果我们没有任何选项,为什么这个参数不只是在创建类型时隐式设置的呢

注意:我意识到这不是vulkan API特有的东西


更新:我不是专门谈论vulkan,而是所有只能是特定类型的参数。

该设计允许将结构链接在一起,以便扩展可以为现有调用创建附加参数,而不会干扰原始API结构,也不会相互干扰

Vulkan中几乎每个结构的第一个成员都是
sType
,第二个成员都是
pNext
。这意味着,如果你有一个
void*
,你只知道它是某种Vulkan API结构,你可以安全地读取前32位,它将是
VkStructureType
,然后读取下一个32或64位,它会告诉你链中是否有其他结构

例如,有一个
VkMemoryAllocateInfo
结构用于分配内存,除了
sType
pNext
分配的大小和它应该来自的堆索引之外。但是如果我想使用“专用分配”呢扩展。然后我还需要用额外的信息填写一个
VKMemoryIdecatedAllocateInfo
结构。但是我仍然需要调用相同的
vkAllocateMemory
函数,该函数只接受一个
VkMemoryAllocateInfo
…那么我应该把我填写的
VKMemoryIdecatedAllocateInfo
结构放在哪里呢在
VkMemoryAllocateInfo
pNext
字段中指向它

也许我也想和一些OpenGL代码共享这个内存。有一个扩展可以让你这样做,但是你需要填写一个
VkExportMemoryAllocateInfo
结构,并在分配过程中传递它。好吧,我可以把它放在我的
vkmemorydivitedallocateinfo
pNext
字段中结构。我可以创建这样的结构链,只要我想

这是真正重要的部分。由于所有结构的第一个字段都是
sType
,因此扩展可以沿着这条结构链导航并找到它所关心的结构,而不知道任何关于结构的信息,除了它们总是以
sType
pNext
开头

所有这些都意味着Vulkan可以通过改变现有函数行为的方式进行扩展,但不改变函数本身或传递给它的结构

您可能会问,为什么所有的核心结构都有
sType
pNext
,即使您将它们传递给带有类型指针的函数,而不是空指针。原因是一致性,而且您永远不知道什么时候可能需要现有结构作为某些新扩展链的一部分

如果我们没有任何选项,为什么这个参数不只是在创建类型时隐式设置的呢

<>因为C不是C++,没有办法在C中声明一个结构,并说这个结构的一部分总是有这个值。在C++中,你可以通过声明一些东西作为const并提供初始默认值。事实上,我喜欢Vulkan C++绑定的一个事情是,你基本上可以忘记<代码> Stpede>永久。如果您正在使用扩展,您仍然需要根据需要填充
pNext

可能重复的
typedef struct VkInstanceCreateInfo {
    VkStructureType             sType;
    const void*                 pNext;
    VkInstanceCreateFlags       flags;
    const VkApplicationInfo*    pApplicationInfo;
    uint32_t                    enabledLayerCount;
    const char* const*          ppEnabledLayerNames;
    uint32_t                    enabledExtensionCount;
    const char* const*          ppEnabledExtensionNames;
} VkInstanceCreateInfo;