代码应该从用户获取一个坐标数组,然后对该数组进行排序,将坐标按它们与原点的距离的顺序排列。我相信我的问题在于排序功能(我使用了快速排序)。
我正在尝试自己编写函数以更好地理解它,这就是为什么我没有使用qsort()
。
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#define MAX_SIZE 64
typedef struct
{
double x, y;
}POINT;
double distance(POINT p1, POINT p2);
void sortpoints(double distances[MAX_SIZE], int firstindex, int lastindex, POINT data[MAX_SIZE]);
void printpoints(POINT data[], int n_points);
int main()
{
int n_points, i;
POINT data[MAX_SIZE], origin = { 0, 0 };
double distances[MAX_SIZE];
printf("How many values would you like to enter?\n");
scanf("%d", &n_points);
printf("enter your coordinates\n");
for (i = 0; i < n_points; i++)
{
scanf("%lf %lf", &data[i].x, &data[i].y);
distances[i] = distance(data[i], origin); //data and distances is linked by their index number in both arrays
}
sortpoints(distances, 0, i, data);
return 0;
}
double distance(POINT p1, POINT p2)
{
return sqrt(pow((p1.x - p2.x), 2) + pow((p1.y - p2.y), 2));
}
void printpoints(POINT *data, int n_points)
{
int i;
printf("Sorted points (according to distance from the origin):\n");
for (i = 0; i < n_points; i++)
{
printf("%.2lf %.2lf\n", data[i].x, data[i].y);
}
}
//quicksort
void sortpoints(double distances[MAX_SIZE], int firstindex, int lastindex, POINT data[MAX_SIZE])
{
int indexleft = firstindex;
int indexright = lastindex;
int indexpivot = (int)((lastindex + 1) / 2);
int n_points = lastindex + 1;
double left = distances[indexleft];
double right = distances[indexright];
double pivot = distances[indexpivot];
POINT temp;
if (firstindex < lastindex) //this will halt the recursion of the sorting function once all the arrays are 1-size
{
while (indexleft < indexpivot || indexright > indexpivot) //this will stop the sorting once both selectors reach the pivot position
{
//reset the values of left and right for the iterations of this loop
left = distances[indexleft];
right = distances[indexright];
while (left < pivot)
{
indexleft++;
left = distances[indexleft];
}
while (right > pivot)
{
indexright--;
right = distances[indexright];
}
distances[indexright] = left;
distances[indexleft] = right;
temp = data[indexleft];
data[indexleft] = data[indexright];
data[indexright] = temp;
}
//recursive sorting to sort the sublists
sortpoints(distances, firstindex, indexpivot - 1, data);
sortpoints(distances, indexpivot + 1, lastindex, data);
}
printpoints(data, n_points);
}
感谢您的帮助,我一直在尝试调试这几个小时,甚至使用调试器。
答案 0 :(得分:2)
哎哟!您以sortpoints()
为参数调用i
。根据您的原型和代码,该论点应为last index
,而i
不是last index
,而是last index + 1
。
int indexleft = firstindex;
int indexright = lastindex; // indexright is pointing to a non-existent element.
int indexpivot = (int)((lastindex + 1) / 2);
int n_points = lastindex + 1;
double left = distances[indexleft];
double right = distances[indexright]; // now right is an undefined value, or segfault.
要解决此问题,请将您的sortpoints()
功能称为:
sortpoints (0, n_points-1, data);
答案 1 :(得分:0)
问题出在您的sortpoints
功能中。第一个while
循环无限循环。要测试它是无限循环还是不放置printf
语句
printf("Testing first while loop\n");
在您的第一个while
循环中。你必须解决这个问题。
答案 2 :(得分:0)
有很多问题,但其中一个是:
int indexpivot = (int)((lastindex + 1) / 2);
演员阵容是不必要的,但这是琐事。更为基本的是,如果你从48..63中对一个片段进行排序,你将在元素32上进行旋转,这不在你应该处理的范围内。你需要使用:
int indexpivot = (lastindex + firstindex) / 2;
或者也许:
int indexpivot = (lastindex + firstindex + 1) / 2;
对于示例范围,它们将在元素55或56上进行旋转,这至少在范围内。
我强烈建议:
创建类似于printpoints()
的打印功能,但有以下不同之处:
在递归之前在sort函数中使用此函数。
这允许您检查分区是否正常工作(目前不是)。
然后,当您的代码正常工作时,您可以在排序功能中删除或禁用(注释掉)打印代码。