0

我想知道您是否可以帮助我调试我的一些代码。我已经为一个我们正在实现多边形逼近算法的类项目编写了以下代码。但我似乎无法让代码做我想做的事情。这是该算法的维基文章的链接:http ://en.wikipedia.org/wiki/Ramer%E2%80%93Douglas%E2%80%93Peucker_algorithm

我遇到的问题是第二个数组 closedStack 要么没有正确更新内部的值,要么没有正确显示。但是第一个数组,即从文件中读取的数组正确显示。我还不断收到已满的 closedStack 错误,因此我将 if 语句更改为不使用 fileSize 变量,因此它也可能存在问题。如果您需要我解释任何逻辑或变量等,请询问,我会解释。

#include "math.h"
#include <iostream>
#include <fstream>
#include "glut.h"

using namespace std;

struct point{
    int x, y;
};

void display(void);
void fileRead();
void oPush(point);
void cPush(point);
point oPop();
int deviation();

point pixel[2000];
int fileSize = 0;
int errorAllowed= 5;
int errorDeviation=0;
int oTop = 0;
int cTop = 0;
point first;
point last;
point openStack[5000];
point closedStack[5000];
int V1 = 0;
int V2 = 0;

void main(int argc, char **argv){

    fileRead();

    glutInit(&argc, argv);
    glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB);
    glutInitWindowSize(500,500);
    glutInitWindowPosition(75,75);
    glutCreateWindow("Ramer's Iterative Algorithm");
    glutDisplayFunc(display);
    gluOrtho2D(0,500,0,500);

    fileSize = fileSize/2;

    int tmp1 = pixel[0].x+pixel[0].y;
    int tmp2 = 0;


    for(int i = 0; i<2000; i++){
        tmp2 = pixel[i].x+pixel[i].y;

        if(tmp2 < tmp1){
            tmp1 = tmp2;
            V1 = i;
        }
    }

    for(int i = 0; i<2000; i++){
        tmp2 = pixel[i].x+pixel[i].y;

        if(tmp2 > tmp1){
            tmp1 = tmp2;
            V2 = i;
        }
    }

    oPush(pixel[V1]);
    oPush(pixel[V2]);
    oPush(pixel[V1]);

    do{
        first = oPop();
        last = oPop();

        int Mid = deviation();

        if(errorDeviation>errorAllowed){
            oPush(last);
            oPush(pixel[Mid]);
            oPush(first);
        }

        else if(errorDeviation<=errorAllowed){
            oPush(last);
            cPush(first);
        }

    }while(oTop>=2);

    glutMainLoop();

    cin >> V1;

}

void display(void){
    glClearColor(0,0,0,0);
    glClear(GL_COLOR_BUFFER_BIT);
    glColor3f(1,1,1);

    glBegin(GL_POINTS);
    for(int i=0; i<2000; i++)
        glVertex2i(pixel[i].x,pixel[i].y);
    glEnd();

    glColor3f(1,0,0);
    glBegin(GL_LINE_STRIP);
    for(int i=0;i<=cTop; i++)
        glVertex2i(closedStack[i].x,closedStack[i].y);
    glEnd();

    glFlush();
}

void fileRead(){
    char fileName[20];

    cout << "Enter the name of the file you would like to parse data from: ";
    cin >> fileName;

    ifstream boundary;
    boundary.open(fileName);
    if(boundary.fail()){
        cout << "Could not open '" << fileName << "' for reading.\n";
        exit(0);
    }

    for(int i=0; !boundary.eof(); i++){
        boundary >> pixel[i].x;
        boundary >> pixel[i].y;
        fileSize ++;
    }

}

void oPush(point p){
    if(oTop>fileSize){
        cout << "Full Stack--Open\n";
        exit(0);
    }

    else{
        oTop++;
        openStack[oTop]= p;
    }
}

void cPush(point p){
    if(cTop>10000){
        cout << "Full Stack--Closed\n";
        exit(0);
    }

    else{
        cTop++;
        closedStack[cTop]= p;
    }
}

point oPop(){
    point temp;

    if(oTop<=0){
        cout << "Stack Empty\n";
        exit(0);
    }

    else{
        temp = pixel[oTop];
        oTop--;
    }
    return temp;
}

int deviation(){
    float y = last.y-first.y;
    float x = last.x-first.x;
    float theta = atan(y/x);
    int most = 0;

    for(int i = V1+1; i < V2; i++){
        float ped = (-(pixel[i].x-first.x)*sin(theta))+((pixel[i].y-last.y)*cos(theta));
        float errDev= abs(ped);

        if(errDev>most)
            most = i;
        errorDeviation = (int)errDev;
    }

    return most;
}

为了详细说明 V1 和 V2,它们应该是数组的左下角和右上角。检查我的循环已简化为:

for(int i = 0; i<fileSize; i++){
tmp2 = (pixel[i].x)+(pixel[i].y);

if(tmp2 <= tmp1){
    tmp1 = tmp2;
    V1 = i;
}

if(tmp2 >= tmp1){
    tmp1 = tmp2;
    V2 = i;
}

循环将点的 x+y 加在一起,然后将其与前一个点进行检查以更新它。x+y 最低的点最终应该是 V1,最高的点应该是 V2。但我认为循环运行不正常。通过放大绘制的内容,显示循环的第二部分只有三个点。它看起来像初始数组的第一个和第二个点以及 0,0 被绘制。不知道为什么会这样。

4

1 回答 1

0

就目前而言,您的问题实在是太宽泛了。您需要尝试自己缩小范围。这是一个很好的清单: http: //msmvps.com/blogs/jon_skeet/archive/2012/11/24/stack-overflow-question-checklist.aspx

您不会通过尝试一次性编写完整的工作程序来解决您的问题。视觉输出是无价的,但它不能代替实际点列表的文本输出。您的问题和评论表明您只是通过查看最终的视觉输出来尝试调试它。您需要将其分解为更小的部分,并查看每个步骤之间的数据,以便您了解您的程序与您的预期不同的地方。

正如您所说的“第二个数组, closedStack 要么没有正确更新内部的值,要么没有正确显示”。解决这个问题的第一步是找出这些情况中的哪一个!数组是否有错误的值,或者显示不正确?您可以通过打印中间值并将它们与手动解决问题时的期望值进行比较来发现这一点。如果输入太大,请创建一组较小的输入点,您可以手动处理。一旦你缩小了范围,你会发现你可以自己解决问题,或者你有一个更集中的问题要问,这会得到更好的答案。


从粗略的检查来看,我猜:

  1. 您似乎误解了输入。你没有描述它是什么。如果它是形成分段线性曲线的点序列,那么不清楚为什么选择最西南和最东北的元素会有所帮助(假设东是+ve x 和北+ve y) . 如果它是一堆点,那么您需要做的不仅仅是挑出角落以使其余部分以有意义的顺序排列。
  2. 您的函数似乎deviation()假设 index first小于 index last。但似乎没有什么可以保证这一点。首先,也许 V1 比 V2 具有更大的索引。即使没有,您也可以使用 [V1, V2, V1] 填充初始堆栈,保证deviation()将看到输入 where first> last。虽然我当然不会保证 没有任何问题deviation(),但我的猜测是您输入的内容存在问题。
于 2012-11-26T09:45:50.893 回答