六边形网格 - 路径不正确

时间:2015-12-01 21:29:56

标签: c++ arrays struct queue hexagonal-tiles

我正在编写一个使用六边形贴图的程序(显然在下面看到的输出中显示为正方形,但数字对六边形形状有意义)从某一点生成路径。 0表示目标,-2表示禁区部分,任何其他数字表示从该点到目标的距离(0)。我写了6个函数来填充周围的邻居。这些函数提供给另一个填充地图的函数..或者应该填充。我发现在某些输入中,地图填充在左侧部分出错。我已经完成了桌面检查,无法找出原因。任何新鲜的眼睛都会有很大的帮助,我已经看了一段时间了:

       struct Point {
            int r;
            int c;
        };

        Queue <Point> q;

        Point getNeighbors1(int r, int c) {
        int n1r, n1c;

                if (r < (ROW-1) ) {
                    n1r = r+1;
                    n1c = c;

                    Point neighborLoc1;
                    neighborLoc1.r = n1r;
                    neighborLoc1.c = n1c;

                    return neighborLoc1;
                }
        }

        Point getNeighbors2(int r, int c) {
        int n2r, n2c;

                if (r > 0) {
                    n2r = r-1;
                    n2c = c;

                    Point neighborLoc2;
                    neighborLoc2.r = n2r;
                    neighborLoc2.c = n2c;

                    return neighborLoc2;
                }
        }

        Point g

etNeighbors3(int r, int c) {
    int n3r, n3c;

            if (c < (COL-1) ) {
                n3r = r;
                n3c = c+1;

                Point neighborLoc3;
                neighborLoc3.r = n3r;
                neighborLoc3.c = n3c;

                return neighborLoc3;
            }
    }

    Point getNeighbors4(int r, int c) {
    int n4r, n4c;


            if (c > 0) {
                n4r = r;
                n4c = c-1;

                Point neighborLoc4;
                neighborLoc4.r = n4r;
                neighborLoc4.c = n4c;

                return neighborLoc4;
            }
    }

    Point getNeighbors5(int r, int c) {
    int n5r, n5c;

        if (c % 2 == 0) {
            if (r > 0 && c < COL-1 ) {
                n5r = r-1;
                n5c = c+1;

                Point neighborLoc5;
                neighborLoc5.r = n5r;
                neighborLoc5.c = n5c;

                return neighborLoc5;
            }
        }
        else {
            if (r < (ROW-1) && c < (COL-1) ) {
                n5r = r+1;
                n5c = c+1;

                Point neighborLoc5;
                neighborLoc5.r = n5r;
                neighborLoc5.c = n5c;

                return neighborLoc5;
            }

        }

    }

    Point getNeighbors6(int r, int c) {
    int n6r, n6c;

        if (c % 2 == 0) {
            if (r > 0 && c > 0) {
                n6r = r-1;
                n6c = c-1;

                Point neighborLoc6;
                neighborLoc6.r = n6r;
                neighborLoc6.c = n6c;

                return neighborLoc6;
            }
        }
        else {
            if (r < (ROW-1) && c > 0) {
                n6r = r+1;
                n6c = c-1;

                Point neighborLoc6;
                neighborLoc6.r = n6r;
                neighborLoc6.c = n6c;

                return neighborLoc6;
            }
        }

    }

    //populate grid
    void numberScheme (Queue<Point> pQ, int map[ROW][COL]) {
        while (!pQ.isEmpty()) {

            Point p = pQ.dequeue();

            Point n1 = getNeighbors1(p.r, p.c);
            if (map[n1.r][n1.c] == -1) {
                map[n1.r][n1.c] = map[p.r][p.c] + 1;
                pQ.enqueue(n1);
            }

            Point n2 = getNeighbors2(p.r, p.c);
            if (map[n2.r][n2.c] == -1) {
                map[n2.r][n2.c] = map[p.r][p.c] + 1;
                pQ.enqueue(n2);
            }

            Point n3 = getNeighbors3(p.r, p.c);
            if (map[n3.r][n3.c] == -1) {
                map[n3.r][n3.c] = map[p.r][p.c] + 1;
                pQ.enqueue(n3);
            }

            Point n4 = getNeighbors4(p.r, p.c);
            if (map[n4.r][n4.c] == -1) {
                map[n4.r][n4.c] = map[p.r][p.c] + 1;
                pQ.enqueue(n4);
            }

            Point n5 = getNeighbors5(p.r, p.c);
            if (map[n5.r][n5.c] == -1) {
                map[n5.r][n5.c] = map[p.r][p.c] + 1;
                pQ.enqueue(n5);
            }

            Point n6 = getNeighbors6(p.r, p.c);
            if (map[n6.r][n6.c] == -1) {
                map[n6.r][n6.c] = map[p.r][p.c] + 1;
                pQ.enqueue(n6);
            }

        }
    }

一些示例输入:目标位于(12,12),非限制单元格:(1,19)。我得到了这个烂摊子:

 9  9 10 11 12 13 14 14 14 13 13 12 12 12 13 13 14 14 15 15 
 8  9 10 11 12 13 14 13 13 12 12 11 11 11 12 12 13 13 14 -2 
 9 10 10 11 12 13 13 12 12 11 11 10 10 10 11 11 12 12 13 13 
10 11 11 12 12 12 12 11 11 10 10  9  9  9 10 10 11 11 12 12 
11 12 12 12 12 11 11 10 10  9  9  8  8  8  9  9 10 10 11 11 
11 11 12 11 11 10 10  9  9  8  8  7  7  7  8  8  9  9 10 10 
10 10 11 10 10  9  9  8  8  7  7  6  6  6  7  7  8  8  9  9 
 9  9 10  9  9  8  8  7  7  6  6  5  5  5  6  6  7  7  8  8 
 8  9 10  9  8  7  7  6  6  5  5  4  4  4  5  5  6  6  7  7 
 8  9 10  9  8  7  6  5  5  4  4  3  3  3  4  4  5  5  6  7 
 8  9 10  9  8  7  6  5  4  3  3  2  2  2  3  3  4  5  6  7 
 8  9 10  9  8  7  6  5  4  3  2  1  1  1  2  3  4  5  6  7 
 8  9 10  9  8  7  6  5  4  3  2  1  0  1  2  3  4  5  6  7 
 8  9 10  9  8  7  6  5  4  3  2  2  1  2  2  3  4  5  6  7 
 8  9 10  9  8  7  6  5  4  4  3  3  2  3  3  4  4  5  6  7 
 8  9 10  9  8  7  6  6  5  5  4  4  3  4  4  5  5  6  6  7 
 9 10 10  9  8  8  7  7  6  6  5  5  4  5  5  6  6  7  7  8 
10 10 10 10  9  9  8  8  7  7  6  6  5  6  6  7  7  8  8  9 
 9  9 10 11 10 10  9  9  8  8  7  7  6  7  7  8  8  9  9 10 
 8  9 10 11 11 11 10 10  9  9  8  8  7  8  8  9  9 10 10 11 

1 个答案:

答案 0 :(得分:0)

看起来你计算方向的方式是关闭的。您最好将它们命名为getNeighborsxgetNorthNeighborgetSouthNeighborgetNortheastNeighborgetSouthwestNeighbor,{{getNorthwestNeighbor,而不是getSoutheastNeighbor。 1}},因为这样可以很容易地确定哪些功能正在做什么以及为什么它们可能没有按预期运行。

当我制作六边形网格时,我定义了这样的方向:

enum direction {
    north, south, northeast, southwest, northwest, southeast
};

我从这样的方向得到了相对的分数:

point point::getRelativePoint(const direction & d) const {
    switch (d) {
    case north: return point(x + 1, y); //North and south are defined along the X axis, for our purposes
    case south: return point(x - 1, y);
    case northeast: return point(x, y + 1); //Northeast and Southwest are defined along the Y axis
    case southwest: return point(x, y - 1);
    case southeast: return point(x - 1, y + 1); //Northwest and Southeast can be defined by adding together other directions: Northwest is North + Southwest, and Southeast is South + Northeast.
    case northwest: return point(x + 1, y - 1);
    }
}

您的getNeighbors5getNeighbors6函数是我认为有问题的,因为它们会根据可疑标准改变方向:

Point getNeighbors5(int r, int c) {
    int n5r, n5c;

    if (c % 2 == 0) {
        if (r > 0 && c < COL-1 ) {
            n5r = r-1;
            n5c = c+1;

            Point neighborLoc5;
            neighborLoc5.r = n5r;
            neighborLoc5.c = n5c;

            return neighborLoc5;
        }
    }
    else {
        if (r < (ROW-1) && c < (COL-1) ) {
            n5r = r+1;
            n5c = c+1;

            Point neighborLoc5;
            neighborLoc5.r = n5r;
            neighborLoc5.c = n5c;

            return neighborLoc5;
        }

    }
}

根据它所在的列改变哪个方向是没有意义的。一个单元格的东南方(如果它被定义为South和NorthEast的复合)总是为-1,+ 1个单元格。

我附上了六边形网格的图像,我建议你用它来计算出这些细胞的位置。根据你如何定义North / NorthEast,你可能需要旋转我提供的Axis的方向,但它应该照亮你可能出错的地方。

image of hexagonal grid