c++ - 我们不能在 C++ 中不使用指向对象的指针来创建节点吗?
问题描述
我在黑客等级的链接列表上解决了这个问题:https ://www.hackerrank.com/challenges/insert-a-node-at-the-head-of-a-linked-list/
并得到给定代码的正确答案。大部分代码都是预先编写好的;我只需要完成函数 insertNodeAtHead 函数(封闭在三颗星之间):
#include <bits/stdc++.h>
using namespace std;
class SinglyLinkedListNode {
public:
int data;
SinglyLinkedListNode *next;
SinglyLinkedListNode(int node_data) {
this->data = node_data;
this->next = nullptr;
}
};
class SinglyLinkedList {
public:
SinglyLinkedListNode *head;
SinglyLinkedListNode *tail;
SinglyLinkedList() {
this->head = nullptr;
this->tail = nullptr;
}
};
void print_singly_linked_list(SinglyLinkedListNode* node, string sep, ofstream& fout) {
while (node) {
fout << node->data;
node = node->next;
if (node) {
fout << sep;
}
}
}
void free_singly_linked_list(SinglyLinkedListNode* node) {
while (node) {
SinglyLinkedListNode* temp = node;
node = node->next;
free(temp);
}
}
// Complete the insertNodeAtHead function below.
/*
* For your reference:
*
* SinglyLinkedListNode {
* int data;
* SinglyLinkedListNode* next;
* };
*
*/
***SinglyLinkedListNode* insertNodeAtHead(SinglyLinkedListNode* llist, int data) {
SinglyLinkedListNode *nnode;
nnode = new SinglyLinkedListNode(data);
if(llist !=NULL)
nnode->next=llist;
return llist=nnode;
}***
int main()
{
ofstream fout(getenv("OUTPUT_PATH"));
SinglyLinkedList* llist = new SinglyLinkedList();
int llist_count;
cin >> llist_count;
cin.ignore(numeric_limits<streamsize>::max(), '\n');
for (int i = 0; i < llist_count; i++) {
int llist_item;
cin >> llist_item;
cin.ignore(numeric_limits<streamsize>::max(), '\n');
SinglyLinkedListNode* llist_head = insertNodeAtHead(llist->head, llist_item);
llist->head = llist_head;
}
print_singly_linked_list(llist->head, "\n", fout);
fout << "\n";
free_singly_linked_list(llist->head);
fout.close();
return 0;
}
我只需要完成 insertNodeAtHead() 函数。休息都已经在那里了。但是,当我尝试在不使用 SinglyLinkedListNode 类类型(它们的预定义类)的指针 nnode 对象(我的标识符)的情况下执行此操作时,我得到编译错误:
#include <bits/stdc++.h>
using namespace std;
class SinglyLinkedListNode {
public:
int data;
SinglyLinkedListNode * next;
SinglyLinkedListNode(int node_data) {
this - > data = node_data;
this - > next = nullptr;
}
};
class SinglyLinkedList {
public:
SinglyLinkedListNode * head;
SinglyLinkedListNode * tail;
SinglyLinkedList() {
this - > head = nullptr;
this - > tail = nullptr;
}
};
void print_singly_linked_list(SinglyLinkedListNode * node, string sep, ofstream & fout) {
while (node) {
fout << node - > data;
node = node - > next;
if (node) {
fout << sep;
}
}
}
void free_singly_linked_list(SinglyLinkedListNode * node) {
while (node) {
SinglyLinkedListNode * temp = node;
node = node - > next;
free(temp);
}
}
// Complete the insertNodeAtHead function below.
/*
* For your reference:
*
* SinglyLinkedListNode {
* int data;
* SinglyLinkedListNode* next;
* };
*
*/
***SinglyLinkedListNode * insertNodeAtHead(SinglyLinkedListNode * llist, int data) {
SinglyLinkedListNode nnode;
nnode = new SinglyLinkedListNode(data);
if (llist != NULL)
nnode.next = llist;
return llist = & nnode;
}***
int main() {
ofstream fout(getenv("OUTPUT_PATH"));
SinglyLinkedList * llist = new SinglyLinkedList();
int llist_count;
cin >> llist_count;
cin.ignore(numeric_limits < streamsize > ::max(), '\n');
for (int i = 0; i < llist_count; i++) {
int llist_item;
cin >> llist_item;
cin.ignore(numeric_limits < streamsize > ::max(), '\n');
SinglyLinkedListNode * llist_head = insertNodeAtHead(llist - > head, llist_item);
llist - > head = llist_head;
}
print_singly_linked_list(llist - > head, "\n", fout);
fout << "\n";
free_singly_linked_list(llist - > head);
fout.close();
return 0;
}
编译后的错误:
solution.cc:在函数'SinglyLinkedListNode * insertNodeAtHead(SinglyLinkedListNode *,int)'中:solution.cc:63:24:错误:没有匹配函数调用'SinglyLinkedListNode :: SinglyLinkedListNode()'SinglyLinkedListNode nnode; ^~~~~ solution.cc:10:9: 注意: 候选: 'SinglyLinkedListNode::SinglyLinkedListNode(int)' SinglyLinkedListNode(int node_data) { ^~~~~~~~~~~~~~~~~~ ~~ solution.cc:10:9:注意:候选人需要 1 个参数,0 提供了 solution.cc:5:7:注意:候选人:'constexpr SinglyLinkedListNode::SinglyLinkedListNode(const SinglyLinkedListNode&)' class SinglyLinkedListNode { ^~~~~ ~~~~~~~~~~~~~~~ solution.cc:5:7: note: 候选人需要 1 个参数,0 提供 solution.cc:5:7: note: Candidate: 'constexpr SinglyLinkedListNode:: SinglyLinkedListNode(SinglyLinkedListNode&&)' solution.cc:5:7: 注意:候选人需要 1 个参数,0 提供 solution.cc:64:40: 错误:'operator=' 的重载不明确(操作数类型是 'SinglyLinkedListNode' 和 'SinglyLinkedListNode* ') nnode = new SingleLinkedListNode(data); ^ solution.cc:5:7: 注意:候选:'SinglyLinkedListNode& SinglyLinkedListNode::operator=(const SinglyLinkedListNode&)' class SinglyLinkedListNode { ^~~~~~~~~~~~~~~~~~~~解决方案。 cc:5:7:注意:参数 1 的转换格式错误:solution.cc:64:11:错误:用户定义的从“SinglyLinkedListNode*”到“const SinglyLinkedListNode&”的转换无效 [-fpermissive] nnode = new单链表节点(数据);^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 解决方案.cc:10:9:
nnode = new SingleLinkedListNode(data); ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ solution.cc:64:11:错误:从'SinglyLinkedListNode*'到'int'的无效转换' [-fpermissive] solution.cc:10:34: 注意:初始化参数 1 的 'SinglyLinkedListNode::SinglyLinkedListNode(int)' SinglyLinkedListNode(int node_data) { ~~~~^~~~~~~~~ solution.cc :5:7: 注意:候选:'SinglyLinkedListNode& SinglyLinkedListNode::operator=(SinglyLinkedListNode&&)' class SinglyLinkedListNode { ^~~~~~~~~~~~~~~~~~~~ solution.cc:5:7 :注意:参数 1 的转换格式不正确:solution.cc:64:11:错误:从“SinglyLinkedListNode*”到“SinglyLinkedListNode&&”的用户定义转换无效 [-fpermissive] nnode = new SinglyLinkedListNode(data);
nnode = new SingleLinkedListNode(data); ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ solution.cc:64:11:错误:从'SinglyLinkedListNode*'到'int'的无效转换' [-fpermissive] solution.cc:10:34: 注意:初始化参数 1 的 'SinglyLinkedListNode::SinglyLinkedListNode(int)' SinglyLinkedListNode(int node_data) { ~~~~^~~~~~~~~ solution.cc :64:40:错误:从'SinglyLinkedListNode'类型的右值转换为非常量引用类型'class SinglyLinkedListNode&&' [-fpermissive] nnode = new SinglyLinkedListNode(data);
退出状态 255
我坚信它应该有效,但事实并非如此。由于逻辑相同,唯一的区别是我没有使用指针来创建对象。 由于我是 C++ 新手,我无法弄清楚为什么会发生这种情况。请给出见解。
解决方案
我们可以在没有指针的情况下创建节点吗...
技术上是的,但实际上不是。在这种情况下不是。
SinglyLinkedListNode nnode;
失败是因为没有构造函数SinglyLinkedListNode
不带参数。
SinglyLinkedListNode nnode(data);
或者
SinglyLinkedListNode nnode{data};
调用SinglyLinkedListNode(int node_data)
并创建一个SinglyLinkedListNode
,但这SinglyLinkedListNode
是一个局部范围的自动变量。它会在insertNodeAtHead
返回后立即销毁。这对你没用。你最终会得到一个所谓的悬空指针,一个指向死对象的指针。访问该死对象是未定义的行为。这通常是致命的,但信不信由你,当它不致命时,情况会更糟。你不知道会发生什么。通常,该程序看起来可以正常工作。然后突然之间就没有了。
您需要动态分配,而保持动态分配的最简单方法是使用指针。
边注:
return llist = nnode;
也可能是
return nnode;
这里的任务什么都不做。指针是指向对象的地址。当您将指针传递给函数时,指向的对象是通过引用传递的,但函数会获得地址的副本。llist = nnode
更改地址的副本,而不是原始地址。调用函数不知道副本会发生什么,并继续使用它的原始值。
在这种情况下,你有点走运,因为
return llist = nnode;
执行无意义的赋值,然后返回 的值llist
,即无论如何您想要返回的值。
推荐阅读
- reactjs - Apache 重写规则不适用于 HTTPS(反应路由器)
- python - 解码字节序列 - 这样做的思路是什么
- jquery-select2 - 克隆 div 后,多个 select2 jquery 不起作用
- java - 并发和 JPA 存储库行为
- python - 熊猫 | 读取_csv | to_xml | ValueError:无效的标签名称'foo bar'
- java - 如何将存储的 MS SQL Server 函数映射到 Spring Data JPA 存储库方法
- dialogflow-es - 当用户触发意图时如何存储数据?
- node.js - 如何将用户输入的日期更改为用户时区nodejs
- javascript - 使用 Django 通道将 OpenCV 图像从 Python 传输到 JavaScript
- javascript - 输入时间 html,验证不允许超过 59 反应句柄变化