gpt4 book ai didi

c++ - 使用数组下标运算符访问结构成员

转载 作者:太空宇宙 更新时间:2023-11-03 10:21:34 25 4
gpt4 key购买 nike

假设有一个类型 T 和一个仅包含 T 类型的统一元素的结构。

struct Foo {
T one,
T two,
T three
};

我想以休闲方式访问它们:

struct Foo {
T one,
T two,
T three

T &operator [] (int i)
{
return *(T*)((size_t)this + i * cpp_offsetof(Foo, two));
}
};

其中 cpp_offsetof 宏(它被认为是正确的)是:

#define cpp_offsetof(s, m)   (((size_t)&reinterpret_cast<const volatile char&>((((s*)(char*)8)->m))) - 8)

C++ 标准并不能保证这一点,但我们是否可以假设成员之间的距离固定为一个固定的偏移量并且以上是正确的跨平台解决方案?


100% 兼容的解决方案是:

struct Foo {
T one,
T two,
T three

T &operator [] (int i) {
const size_t offsets[] = { cpp_offsetof(Foo, one), cpp_offsetof(Foo, two), cpp_offsetof(Foo, three) };
return *(T*)((size_t)this + offsets[i]);
}
};

[edit]标准、兼容和更快的版本由 snk_kid using pointers to data members 提出[/edit]
但它需要我试图避免的额外查找表。

//编辑
还有一个。我不能只使用数组和常量来索引这些字段,它们必须被命名为结构的字段(某些宏要求这样做)。

//编辑2
为什么必须将这些命名为结构的字段?什么是宏?它是一个更大项目的设置系统。简化它是这样的:

struct Foo {
int one;
int two;
}
foo;

struct Setting { void *obj, size_t filed_offset, const char *name, FieldType type }

#define SETTING(CLASS, OBJ, FIELD, TYPE) { OBJ, cpp_offsetof(CLASS, FIELD), #OBJ #FIELD, TYPE }

Setting settings[] = {
SETTING(Foo, foo, one, INT_FIELD),
SETTING(Foo, foo, two, INT_FIELD)
};

再说一遍:我不是在寻找 100% 兼容的解决方案,而是 99% 兼容的解决方案。我在问我们是否可以预期某些编译器会在统一字段之间放置非统一填充。

最佳答案

您的代码不适用于非 POD 类型,例如那些使用虚拟成员函数的类型。使用指向数据成员的指针,有一种符合标准(且有效)的方法可以实现您想要做的事情:

template< typename T >
struct Foo {

typedef size_t size_type;

private:

typedef T Foo<T>::* const vec[3];

static const vec v;

public:

T one;
T two;
T three;

const T& operator[](size_type i) const {
return this->*v[i];
}

T& operator[](size_type i) {
return this->*v[i];
}
};

template< typename T >
const typename Foo<T>::vec Foo<T>::v = { &Foo<T>::one, &Foo<T>::two, &Foo<T>::three };

只需确保将 const every 与指向数据成员的指针表一起使用即可获得优化。检查here看看我在说什么。

关于c++ - 使用数组下标运算符访问结构成员,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3178347/

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