Pointers 初始化静态指针会导致<;未定义值>; 我在管理C++中只使用指针的初学者问题,这让我头痛。我正在创建一个元素列表,指针应该显示该列表的当前元素
问题是,当我将第一个元素分配给这个列表时,我想用指针(“varPointer=&firstElem”)引用这个列表的开头。但是在那之后,指针就没有任何值了 以下是我的代码的简化版本:Pointers 初始化静态指针会导致<;未定义值>; 我在管理C++中只使用指针的初学者问题,这让我头痛。我正在创建一个元素列表,指针应该显示该列表的当前元素,pointers,c++-cli,Pointers,C++ Cli,问题是,当我将第一个元素分配给这个列表时,我想用指针(“varPointer=&firstElem”)引用这个列表的开头。但是在那之后,指针就没有任何值了 以下是我的代码的简化版本: ref class ElementClass { public: value struct Element { //some items here ...; Element *Next, *Previous; }; ... } ref class Q
ref class ElementClass
{
public:
value struct Element
{
//some items here ...;
Element *Next, *Previous;
};
...
}
ref class Queue
{
public:
static Element* queue;
static void AddElem(Element* elem) {
//Check, if queue is empty
if (queue == nullptr) {
queue = elem;
queue->Previous = nullptr;
}
else {
queue->Next = elem;
elem->Previous = queue;
queue = elem;
}
}
}
程序不会抛出任何错误,在下一次迭代中,列表似乎仍然为空。
即使我用“static Element*queue=0”或队列指针总是有的东西显式初始化队列。无法使用“Element”实例进行初始化(“不能使用'interior_ptr'类型的值初始化'Element*'类型的实体”)。为此,我添加了:
...
public:
static Element^ tmpElem = gcnew Element();
static Element* queue = &tmpElem;
...
程序从不使用else语句。
我感谢任何帮助。提前谢谢大家
(我对编程一般都很熟悉,但我对C++是新手)。
< P>好的。这是教育性的。< /P> 因此,如果使用传统的非托管指针Element *Next = nullptr, *Previous = nullptr;
static void AddElem(ElementClass::Element * elem) {
//Check, if queue is empty
if (queue == nullptr) {
queue = elem;
queue->Previous = nullptr;
}
else {
queue->Next = elem;
elem->Previous = queue;
queue = elem;
}
}
然后使用传递值
static void AddElem(ElementClass::Element elem) {
//Check, if queue is empty
if (queue == nullptr) {
queue = &elem;
queue->Previous = nullptr;
}
else {
queue->Next = &elem;
elem.Previous = queue;
queue = &elem;
}
}
Kablooey!elem
在它进入的过程中被复制,并将超出范围,在返回的过程中被销毁,或者被标记为销毁,并在不久的将来由垃圾收集器在某个时候死亡。我不确定这一点,但它将被销毁,并且很可能在您完成它之前被销毁。这会留下一堆指向无效备忘录的指针如果程序没有崩溃,那不是因为它起作用了,而是因为你运气不好,看起来它起作用了
如果您一直回到C风格:
Element *Next = nullptr, *Previous = nullptr;
然后传入一个非托管指针
Element *Next = nullptr, *Previous = nullptr;
static void AddElem(ElementClass::Element * elem) {
//Check, if queue is empty
if (queue == nullptr) {
queue = elem;
queue->Previous = nullptr;
}
else {
queue->Next = elem;
elem->Previous = queue;
queue = elem;
}
}
它可以工作,但是你必须手工完成所有的内存管理。没有垃圾收集
如果你使用托管指针,你会得到托管内存。很棒的东西
Element ^Next = nullptr, ^Previous = nullptr;
然后
static void AddElem(ElementClass::Element elem) {
//Check, if queue is empty
if (queue == nullptr) {
queue = elem;
queue->Previous = nullptr;
}
else {
queue->Next = elem;
elem.Previous = queue;
queue = elem;
}
}
据我所知,它存储并管理元素的副本,使副本保持活动状态。原始元素不受影响。它不知道它已链接,因为它未被链接。副本已链接。这可能是您所需要的全部。鉴于元素
是一种值类型,这应该是您想要的
否则,请使用端到端托管指针
static void AddElem(ElementClass::Element ^ elem) {
//Check, if queue is empty
if (queue == nullptr) {
queue = elem;
queue->Previous = nullptr;
}
else {
queue->Next = elem;
elem->Previous = queue;
queue = elem;
}
}
注意,我没有改变任何链表逻辑。这很好。< /P>但是我是C++新手,我对这个“管理C++”新手。“你所发布的内容肯定不是C++,至少是ANSI C++。<代码>元素*NETX,*BASEN;<代码>具有指向可能已分配或管理的数据的非托管指针。小心混合托管和非托管指针。很可能这就是编译器警告的。在
void AddElem(Element elem)
elem
中,按值传递。这将导致elem
成为传入内容的临时副本,在退出函数时将被销毁<代码>队列=&elem代码>存储指向此临时副本的指针,并在函数结束和elem
被销毁后指向无效内存。这里是龙。我以为结构和类总是通过引用传递的?恐怕不是。必须明确调用C++中的PASS引用。对内部指针做了更多的阅读。这可能会有帮助:值类型(ref class
)的一部分时。这包括装箱的值。值类型只是引用类型内存的一部分,因此会被清除。C++ + CLI(不管理C++——这是一个遗留物)是一种特殊的野兽:你得到C++的复杂性加上CLR的复杂性,你需要把两者混合在一起。我将元素的所有实例从值类型或非托管指针“*”更改为托管指针“^”。现在很好用。显然我误解了管理指针。。。感谢你们的帮助,特别是@user4581301,他显然花了很长时间进行研究。