由于 RPTR->num=30 与 (*rptr).num=30 相同,但是*((*rptr).ptr).name 不起作用为什么?



我有两个结构

struct temp
{
char name[20];
};
struct abc
{
temp *ptr;
int num;
};

这是主要功能。

main()
{
abc *rptr;
strcpy((rptr->ptr)->name,"Wellcome");
cout<<(rptr->ptr)->name; //works
cout<<*((*rptr).ptr).name; //does not work why?
}

我想知道为什么最后一个cout不起作用。

行:

cout << *((*rptr).ptr).name;

不起作用,因为((*rptr).ptr)上的操作.的优先级高于*

修复它使用:

cout << (*((*rptr).ptr)).name;

重要

请注意,您的代码中有一个更大的问题:

  • 您正在写入未初始化的指针rptr
  • 结构体abc包含指向temp指针,而不是实例

这样做:strcpy((rptr->ptr)->name,"Wellcome");被视为犯罪!你正在腐蚀你所有的记忆!

相反,它应该是这样的:

abc *rptr = new abc();
rptr->ptr = new temp();
strncpy(rptr->ptr->name, "Wellcome", sizeof(rptr->ptr->name));
cout << rptr->ptr->name << endl;
delete rptr->ptr;
delete rptr;

修复:

  • 分配rptr对象
  • rptr中分配ptr对象
  • 仔细复制"Wellcome"字符串(添加边界检查)

由于优先级规则,它不起作用。.(结构成员选择)具有比*(指针去引用)更高的绑定。插上一些括号,效果会很好。请注意,您是如何在内部指针取消引用周围放置括号的,为什么要跳过外部指针?

所以你接受的答案是一个很好的答案,告诉你如何修复你正在做的事情以及为什么它不起作用。

这个答案是告诉你应该做什么。因为你所做的并不是真正的C++。在现代C++中,必须处理指针的情况应该很少见。这是C++相对于C的一个巨大优势,也是我认为选择这种语言的主要原因之一。

以下是您的两个结构的外观:

#include <memory>
#include <string>
struct temp
{
::std::string name;
};
struct abc
{
::std::unique_ptr<temp> ptr;
int num;
};

下面是你的主菜单应该是什么样子的:

#include <iostream>
#include <memory> // Probably redundant, but you do use it directly here.
int main()
{
using ::std::unique_ptr;
using ::std::cout;
using ::std::make_unique;
// If you don't have make_unique (it was added in C++14) use new instead.
unique_ptr<abc> rptr = make_unique<abc>();
rptr->ptr = make_unique<temp>();
rptr->ptr->name = "Wellcome";
cout << (rptr->ptr)->name;
cout << (*(*rptr).ptr).name;
return 0;
}

unique_ptr对象将在超出范围时自动释放它们所指向的对象。因此,第一个rptr消失,因此它指向的abc被销毁,这将销毁abcptr成员,这将导致您分配的temp也被释放。

是的,从技术上讲,这些都是指针,但编译器会为您管理它们的生命周期,这样您就不会有泄漏或意外释放两次。

此外,使用::std::string意味着您根本不必担心像strcpystrlen这样的不安全操作。它会起作用的。

现在,大概你的程序只是一个例子,你有一个更大的程序,你正在实际工作。但这些原则是一样的。除非万不得已,否则不要使用裸指针。使用C++指针类。他们是你的朋友,会让你的生活更轻松。使用标准库中的::std::string::std::vector::std::array和其他类似类。它们会让你的生活轻松很多。

最新更新