gpt4 book ai didi

c++ - 这是 union 的正确用法吗

转载 作者:塔克拉玛干 更新时间:2023-11-03 01:38:17 32 4
gpt4 key购买 nike

我想要命名字段而不是索引字段,但对于某些用途我必须迭代字段。愚蠢的简化示例:

struct named_states {float speed; float position;};

#define NSTATES (sizeof(struct named_states)/sizeof(float))
union named_or_indexed_states {
struct named_states named;
float indexed[NSTATES];
}
...
union named_or_indexed_states states,derivatives;
states.named.speed = 0;
states.named.position = 0;
...
derivatives.named.speed = acceleration;
derivatives.named.position= states.named.speed;
...
/* This code is in a generic library (consider nstates=NSTATES) */
for(i=0;i<nstates;i++)
states.indexed[i] += time_step*derivatives.indexed[i];

这避免了从命名结构到索引数组的复制,反之亦然,并用通用解决方案替换它,因此更容易维护(当我增加状态 vector 时,我几乎没有什么地方可以改变)。它也有效与我测试过的各种编译器(gcc/g++ 和 MSVC 的几个版本)配合得很好。

但理论上,据我所知,它并没有严格遵守正确的 union 用法,因为我写了命名字段然后读取了索引字段,而且我完全不确定我们是否可以说它们共享相同的结构字段......

你能确认它在理论上是坏的(不可移植)吗?

我应该更好地使用强制转换、memcpy() 还是其他东西?

除了理论之外,从实用的 POV 来看,是否存在任何真正的可移植性问题(一些不兼容的编译器、奇异的结构对齐、计划的演化......)?

编辑:您的回答应该对我的意图进行更多澄清:

  • 让程序员专注于特定领域的方程式并将它们从转换函数的维护中解放出来(我不知道如何编写一个通用的方程式,apart cast 或 memcpy 技巧,这些技巧似乎并不更健壮)
  • 通过使用结构(完全由编译器控制)与数组(声明和访问可能会出现更多程序员错误)来增加一点编码安全性
  • 避免使用 enum 或 #define 过多污染命名空间

我需要知道

  • 我偏离标准有多可移植/危险(也许一些具有积极内联的编译器将使用完整的寄存器解决方案并避免任何内存交换破坏技巧),
  • 如果我错过了部分或全部解决上述问题的标准解决方案。

最佳答案

不要求 named_states 中的两个字段以与数组元素相同的方式排列。他们很有可能这样做,但你在那里有一个编译器依赖项。

这是您尝试执行的操作的 C++ 简单实现:

struct named_or_indexed_states {
named_or_indexed_states() : speed(indexed[0], position(indexed[1]) { }
float &speed;
float &position;
float indexed[2];
};

如果由于引用元素过多导致大小增加,请使用访问器:

struct named_or_indexed_states {
float indexed[2];
float& speed() { return indexed[0]; }
float& position() { return indexed[1]; }
};

编译器内联访问器没有问题,因此读取或写入 speed()position() 将与成员数据一样快。不过,您仍然需要写那些烦人的括号。

关于c++ - 这是 union 的正确用法吗,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/11957450/

32 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com