意外输出零 我是C++新手,目前在单链表上练习。不知何故,下面代码的输出总是零。我认为问题在于nextPoint方法,但无论我如何尝试更改引用/取消引用,它都不起作用
问题在哪里?先谢谢你意外输出零 我是C++新手,目前在单链表上练习。不知何故,下面代码的输出总是零。我认为问题在于nextPoint方法,但无论我如何尝试更改引用/取消引用,它都不起作用,c++,linked-list,C++,Linked List,问题在哪里?先谢谢你 // Singly Linked List #include <math.h> #include <iostream> class Point { public: double x, y; Point* next; // constructor Point (double x, double y) { this->x = x;
// Singly Linked List
#include <math.h>
#include <iostream>
class Point {
public:
double x, y;
Point* next;
// constructor
Point (double x, double y) {
this->x = x;
this->y = y;
this->next = NULL;
}
void nextPoint(Point nexti) {
this->next = &nexti;
}
double dist(Point &a, Point &b) {
double dx = a.x - b.x;
double dy = a.y - b.y;
return sqrt(dx*dx - dy*dy);
}
double length() {
Point *iter = this;
double len = 0.0;
while (iter->next != NULL) {
len += dist(*iter, *iter->next);
iter = iter->next;
}
return len;
}
};
int main() {
Point p1(1,1);
Point p2(2,2);
Point p3(5,5);
p1.nextPoint(p2);
p2.nextPoint(p3);
std::cout << p1.length() << std::endl;
return 1;
}
//单链表
#包括
#包括
类点{
公众:
双x,y;
点*下一点;
//建造师
点(双x,双y){
这个->x=x;
这->y=y;
此->下一步=空;
}
无效下一点(下一点){
此->下一步=&nexti;
}
双区(a点、b点){
双dx=a.x-b.x;
双dy=a.y-b.y;
返回sqrt(dx*dx-dy*dy);
}
双倍长度(){
点*iter=这个;
双透镜=0.0;
while(iter->next!=NULL){
len+=dist(*iter,*iter->next);
iter=iter->next;
}
回程透镜;
}
};
int main(){
点p1(1,1);
p2点(2,2);
p3点(5,5);
p1.下一点(p2);
p2.下一点(p3);
std::cout请打开更多编译器警告,您可能会在nextPoint
中收到一条警告,提示您正在永久存储临时变量(nexti
)的地址(在this->next
)
您必须传递要添加的点的地址或引用
void nextPoint(Point *nexti) {
this->next = nexti;
}
p1.nextPoint(&p2);
p2.nextPoint(&p3);
或
旁注:请将NULL
替换为nullptr请打开更多编译器警告,您可能会收到一条警告,在nextPoint
中,您将永久存储临时变量(nexti
)的地址(在this->next
中)
您必须传递要添加的点的地址或引用
void nextPoint(Point *nexti) {
this->next = nexti;
}
p1.nextPoint(&p2);
p2.nextPoint(&p3);
或
旁注:请将NULL
替换为nullptr
您的代码有两个问题:
nextPoint
按值获取其参数,这意味着您正在存储该按值参数的地址,该参数在执行nextPoint
结束后立即失效。将其更改为接受Point&nexti
您的距离计算函数错误。您应该添加平方,而不是减去它们:返回sqrt(dx*dx+dy*dy);
与您的问题无关,但有几种方法可以改进代码:
- 使用构造函数中的mem initialiser列表来初始化成员,而不是分配给他们。这是一个好习惯,因为一旦你开始处理初始化和分配本质上不同的事情(引用、类等),这将非常有用
- 使用
NULL ptr
而不是NULL
,因为后者不是类型安全的
length
应标记为const
,因为它不会修改调用它的对象。请注意,iter
同样已更改为const Point*
:
double length() const {
const Point *iter = this;
double len = 0.0;
while (iter->next != NULL) {
len += dist(*iter, *iter->next);
iter = iter->next;
}
return len;
}
dist
根本不使用此
,因此它可以(也应该)成为静态
成员函数。此外,它应该通过常量和获取其参数,因为它不修改它们:
static double dist(const Point &a, const Point &b) {
double dx = a.x - b.x;
double dy = a.y - b.y;
return sqrt(dx*dx - dy*dy);
}
您的代码有两个问题:
nextPoint
按值获取其参数,这意味着您正在存储该按值参数的地址,该参数在执行nextPoint
结束后立即失效。将其更改为接受Point&nexti
您的距离计算函数错误。您应该添加平方,而不是减去它们:返回sqrt(dx*dx+dy*dy);
与您的问题无关,但有几种方法可以改进代码:
- 使用构造函数中的mem initialiser列表来初始化成员,而不是分配给他们。这是一个好习惯,因为一旦你开始处理初始化和分配本质上不同的事情(引用、类等),这将非常有用
- 使用
NULL ptr
而不是NULL
,因为后者不是类型安全的
length
应标记为const
,因为它不会修改调用它的对象。请注意,iter
同样已更改为const Point*
:
double length() const {
const Point *iter = this;
double len = 0.0;
while (iter->next != NULL) {
len += dist(*iter, *iter->next);
iter = iter->next;
}
return len;
}
dist
根本不使用此
,因此它可以(也应该)成为静态
成员函数。此外,它应该通过常量和获取其参数,因为它不修改它们:
static double dist(const Point &a, const Point &b) {
double dx = a.x - b.x;
double dy = a.y - b.y;
return sqrt(dx*dx - dy*dy);
}
你使用<代码>点和<代码> <代码> < <代码> > b>代码>,但是<代码>点<代码> <代码> NEXTI/<代码>。你理解每个构造的意思吗?你选择了什么类型的参数?BTW,如果你正在学习C++,可能会有用的。<代码>点和<代码>是对象地址,所以通过引用。ce和justPoint
是按值传递的,对吗?因为我不想复制我在dist()
中使用的整个Point对象。因为nextPoint()
不起作用,我对它们做了一些修改。或多或少(Point&
是对Point
的引用,而不是真正的地址)但是,这是一个重要的问题。为什么要按值传递到下一个点
函数?通过尝试和错误随机添加/删除指针/引用/取消引用/任何东西恐怕都不是学习编程的方法(或者至少不擅长)。你在a
和b中使用点&