C++ 创建两个具有重叠内存的变量
C++ Create two variables with overlapping memory
我有两个structs
,Rect
和Point
。遗憾的是,我无法改变它们的执行。
矩形的定义是:
typedef struct Rect
{
int x, y;
int w, h;
} Rect;
Point
的定义是:
typedef struct Point
{
int x, y;
} Point;
我想有效地保留一个 Rect,但隐藏w
/h
成员。
我想知道是否可以使用内存中的相同地址创建一个 Point 对象,以便在每个对象之间共享 x
/y
内存?
我尝试使用 placement new
,它似乎不起作用,以及重新分配地址,这显然也不起作用。
有人有什么想法吗?我知道这可能不是最佳实践,但这将是一个巧妙的技巧,使事情变得更容易使用。
乙尼法特尔
你应该把你的 Rect 隐藏在你自己的类中,提供你需要的接口。像这样:
class MyRect
{
private:
Rect _rect;
public:
MyRect(const Rect& rect);
int& x() { return _rect.x; }
int& y() { return _rect.y; }
}
C++具有布局兼容的概念。 您的 Point
类和Rect
类与布局兼容,因为它们具有共同的初始前缀,并且它们是标准布局(或 C++03 中的普通旧数据(。
这意味着
Rect r = {1,2,3,4};
Point* p = &reinterpret_cast<Point*>(&r);
生成一个指向 Rect r
的x
和y
字段p
Point
指针。 修改*p
的x
和y
字段将修改r
中的值,修改r.x
和r.y
将修改*p
中的值。 嗯,有点。
缺点是混叠和严格混叠的概念。 如果在编译器中关闭严格别名,它将丢失一些优化,但上述方法将起作用。
要使其在严格的混叠下工作,您需要将Rect
和Point
存储在一个联合中:
union MyUnion {
Rect r;
Point p;
};
MyUnion u = Rect{1,2,3,4};
现在,p.x
和p.y
在任何情况下都提到了r.x
和r.y
,其中"允许检查 它们中的任何一个的共同初始部分在任何地方声明 工会的完整类型是可见的"。 因此,在可以看到MyUnion
的地方,您是安全的 - 但是在看不到的地方,编译器可以自由地将指针到Point
修改x
视为无法修改指向Rect
指针的x
。 这对于优化目的很重要,因为没有它,重新排序不变的子表达式几乎是不可能的。
如果你想隐藏w
和h
,也许你可以创建一个基于Rect
值的"临时"Point
并使用这种结构......然后,如果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
成员。
感谢所有回答:)的人
乙尼法特尔
附言我使用的代码是用 C 语言编写的,我正在使用C++与之交互。对不起,忘了提:/
P.P.S.感谢您提供解释工会约阿希姆的链接,我从来没有了解过他们!
- 将字符串存储在c++中的稳定内存中
- C++ 指针的内存地址和指向数组的内存地址如何相同?
- Win32编译器选项和内存分配
- Ardunio UNO解决了多个重叠的定时器循环
- 当vector是tje全局变量时,c++中vector的内存管理
- 带内存和隔离功能的SQLite
- 是否可以通过C++扩展强制多个python进程共享同一内存
- 迭代时从向量和内存中删除对象
- 在C++中打印指向不同基元数据类型的指针的内存地址
- 这个指针和内存代码打印是什么?我不知道是打印垃圾还是如何打印我需要的值
- 多个文件的内存分配错误"在抛出 'std :: bad_alloc' what (): std :: bad_alloc 的实例后终止调用" [C++]
- 为什么示例代码访问IUnknown中已删除的内存
- 英特尔将指令存储在重叠的内存区域
- 如何在c/c++中检查两个任意内存范围是否重叠
- 用于查找范围重叠的更节省内存的算法
- 如何修复 g++ 内存范围重叠
- 两个数组的内存地址重叠
- C++ 创建两个具有重叠内存的变量
- 类初始化过程中的内存重叠
- malloc'd 内存重叠由 std::make_shared 创建的对象