C++ C++;创建两个具有重叠内存的变量
我有两个C++ C++;创建两个具有重叠内存的变量,c++,pointers,struct,C++,Pointers,Struct,我有两个struct,Rect和Point。遗憾的是,我不能改变它们的执行情况 Rect的定义是: typedef struct Rect { int x, y; int w, h; } Rect; 点的定义是: typedef struct Point { int x, y; } Point; 我想有效地保留一个Rect,但要隐藏w/h成员 我想知道是否有可能在内存中使用相同的地址创建点对象,以便在每个对象之间共享x/y内存 我尝试过使用placement new,
struct
,Rect
和Point
。遗憾的是,我不能改变它们的执行情况
Rect的定义是:
typedef struct Rect
{
int x, y;
int w, h;
} Rect;
点的定义是:
typedef struct Point
{
int x, y;
} Point;
我想有效地保留一个Rect,但要隐藏w
/h
成员
我想知道是否有可能在内存中使用相同的地址创建点对象,以便在每个对象之间共享x
/y
内存
我尝试过使用placement new
,但似乎不起作用,也尝试过重新分配地址,但显然也不起作用
有人有什么想法吗?我知道这可能不是最好的做法,但这将是一个巧妙的技巧,让事情变得更简单
hnefatl一个选项是让Rect
从点
派生,以便它继承其成员
typedef struct Rect: struct Point
{
int w, h;
} Rect;
并在需要时使用您喜欢的类型的指针
另一个选择是保留原始类型并使用野生类型转换,如
struct Point* MyPseudoPointPtr= (struct Point*)&MyRect;
这也适用于引用
struct Point& MyPseudoPoint= *(struct Point*)&MyRect;
一个选项是让Rect
从点
派生,以便继承其成员
typedef struct Rect: struct Point
{
int w, h;
} Rect;
并在需要时使用您喜欢的类型的指针
另一个选择是保留原始类型并使用野生类型转换,如
struct Point* MyPseudoPointPtr= (struct Point*)&MyRect;
这也适用于引用
struct Point& MyPseudoPoint= *(struct Point*)&MyRect;
您应该将Rect隐藏在自己的类中,提供所需的接口。比如:
class MyRect
{
private:
Rect _rect;
public:
MyRect(const Rect& rect);
int& x() { return _rect.x; }
int& y() { return _rect.y; }
}
您应该将Rect隐藏在自己的类中,提供所需的接口。比如:
class MyRect
{
private:
Rect _rect;
public:
MyRect(const Rect& rect);
int& x() { return _rect.x; }
int& y() { return _rect.y; }
}
如果你想隐藏w
和h
,也许你可以基于Rect
值创建一个“特别的”点
,并使用此结构。。。然后,如果x
和y
可以不同于原始值,则可以将当前值设置为原始Rect
变量:
Rect original_rect;
// ...
Point point;
point.x = original_rect.x;
point.y = original_rect.y;
// code that use Point instead of Rect
// ...
// Set current values to original variable
original_rect.x = point.x;
original_rect.y = point.y;
另一方面,如果需要同时使用Rect
类和隐藏w
和h
。。。如果您想隐藏w
和h
,则无法执行此操作,也许您可以基于Rect
值创建一个“特殊的”点
,并使用此结构。。。然后,如果x
和y
可以不同于原始值,则可以将当前值设置为原始Rect
变量:
Rect original_rect;
// ...
Point point;
point.x = original_rect.x;
point.y = original_rect.y;
// code that use Point instead of Rect
// ...
// Set current values to original variable
original_rect.x = point.x;
original_rect.y = point.y;
另一方面,如果需要同时使用Rect
类和隐藏w
和h
。。。您不能这样做C++具有布局兼容的概念。您的Point
和Rect
类是布局兼容的,因为它们有一个共同的初始前缀,并且它们是标准布局(或C++03中的普通旧数据)
这意味着
Rect r = {1,2,3,4};
Point* p = &reinterpret_cast<Point*>(&r);
现在p.x
和p.y
在任何上下文中均指r.x
和r.y
,其中“允许检查
其中任何一项声明的共同首字母部分
接头的完整类型可见”。因此,在可以看到MyUnion
的地方,您是安全的——但在看不到的地方,编译器可以自由地将指向-点的指针
修改x
视为无法修改指向-Rect
的指针。这对于优化非常重要,因为如果没有它,对未更改的子表达式重新排序几乎是不可能的。C++具有布局兼容的概念。您的Point
和Rect
类是布局兼容的,因为它们有一个共同的初始前缀,并且它们是标准布局(或C++03中的普通旧数据)
这意味着
Rect r = {1,2,3,4};
Point* p = &reinterpret_cast<Point*>(&r);
现在p.x
和p.y
在任何上下文中均指r.x
和r.y
,其中“允许检查
其中任何一项声明的共同首字母部分
接头的完整类型可见”。因此,在可以看到MyUnion
的地方,您是安全的——但在看不到的地方,编译器可以自由地将指向-点的指针
修改x
视为无法修改指向-Rect
的指针。这对于优化非常重要,因为如果没有它,对未更改的子表达式重新排序几乎是不可能的。根据注释和答案,这似乎是不可能的。哦,好吧,用指针会是一个很好的把戏
我只保留rect,不隐藏w
和h
成员
感谢所有回答的人:)
赫内法特尔
我使用的代码是用C编写的,我用C++与它交互。对不起,忘了提一下:/
p.p.S.谢谢你的链接,解释了一个联盟约阿希姆,我从来没有时间去了解他们 根据评论和回答,这似乎是不可能的。哦,好吧,用指针会是一个很好的把戏
我只保留rect,不隐藏w
和h
成员
感谢所有回答的人:)
赫内法特尔
我使用的代码是用C编写的,我用C++与它交互。对不起,忘了提一下:/
p.p.S.谢谢你的链接,解释了一个联盟约阿希姆,我从来没有时间去了解他们 你的意思是像在一个?typedef结构R{}R代码> C,而不是C++,在C++中,不需要代码> TyPulfF/CODE >,结构名称可以用作类型。你需要的是一个联合体,你说你想让事情变得更简单?那么这就不是办法了,它会使事情变得更加复杂,难以维护,并且会让你的代码冒着被你的意思理解的风险,就像在一个?typedef struct R{}R代码> C,而不是C++,在C++中,不需要代码< TyPulf,结构名称可以用作类型。