邻接矩阵邻居

时间:2016-01-01 17:42:20

标签: matrix graph breadth-first-search depth-first-search connected-components

我有一个0和1的矩阵。我可以从任何细胞开始。我想知道涵盖所有可能的1所需的最小步数(向上,向下,向左,向右)是多少。我可以从0或1开始。

示例:

0 1 0 
1 1 1
0 1 0

从1步开始(2,2)我可以达到所有的1。 我将其与未加权无向图的邻接矩阵联系起来。从任何一点开始,我基本上都需要找到最远的邻居。 如果我只能从顶点开始,我可以简单地使用BFS / DFS并保留一个计数器,但是这会产生问题。

2 个答案:

答案 0 :(得分:0)

虽然您可以将0/1矩阵视为某个图的邻接矩阵,但在这种特殊情况下,您真正​​关心的图是每个节点都是矩阵中的单元并且每个节点都与之相邻的图。在矩阵中与它直接相邻的细胞。

解决此问题的一个选项是运行多个广度优先搜索,一个从图中的每个节点开始,并记录每个节点到图中任何1的最大距离。然后,您可以选择最小化此最大距离的节点。

答案 1 :(得分:0)

我的方法是从起始单元向上扩展&向下,然后通过保持到目前为止的数字步骤,在每一行向两端传播该行。

从起点到单元格的所有路线,无论是垂直移动还是水平移动,都会产生相同的Manhattan Distance

解决方案,Try Here

#include<stdio.h>

// test

int main (void)
{
    int g[5][5] =
    {
      { 1,0,0,0,0 },
      { 0,0,1,0,0 },
      { 0,1,1,1,1 },
      { 1,0,1,0,0 },
      { 0,0,0,1,0 }
    };

    printf("\n 4-way solution = %d \n", mmd4(5,5,g, 2,2));
    printf("\n 8-way solution = %d \n", mmd8(5,5,g, 2,2));

    return 0;
}

8路解决方案

int mmd8(int h, int w, int g[h][w], int x, int y)
{
    putchar('#');
    return max8(mmd8_up   (h,w,g,x-1,y  ,1),
                mmd8_down (h,w,g,x+1,y  ,1),
                mmd8_left (h,w,g,x  ,y-1,1),
                mmd8_right(h,w,g,x  ,y+1,1),

                mmd8_uleft (h,w,g,x-1,y-1,1),
                mmd8_uright(h,w,g,x-1,y+1,1),
                mmd8_dleft (h,w,g,x+1,y-1,1),
                mmd8_dright(h,w,g,x+1,y+1,1));
}

int mmd8_up(int h, int w, int g[h][w], int x, int y, int steps)
{
    if (base_case(h,w,x,y)) return 0;
    putchar('U');
    return max4(g[x][y]?steps:0,
           mmd8_up    (h,w,g,x-1,y  ,steps+1),
           mmd8_uleft (h,w,g,x-1,y-1,steps+1),
           mmd8_uright(h,w,g,x-1,y+1,steps+1));
}

int mmd8_down(int h, int w, int g[h][w], int x, int y, int steps)
{
    if (base_case(h,w,x,y)) return 0;
    putchar('D');
    return max4(g[x][y]?steps:0,
           mmd8_down  (h,w,g,x+1,y  ,steps+1),
           mmd8_dleft (h,w,g,x+1,y-1,steps+1),
           mmd8_dright(h,w,g,x+1,y+1,steps+1));
}

int mmd8_left(int h, int w, int g[h][w], int x, int y, int steps)
{
    if (base_case(h,w,x,y)) return 0;
    putchar('L');
    return max2(g[x][y]?steps:0,
           mmd8_left (h,w,g,x  ,y-1,steps+1),
           mmd8_uleft(h,w,g,x-1,y-1,steps+1),
           mmd8_dleft(h,w,g,x+1,y-1,steps+1));
}

int mmd8_right(int h, int w, int g[h][w], int x, int y, int steps)
{
    if (base_case(h,w,x,y)) return 0;
    putchar('R');
    return max2(g[x][y]?steps:0,
           mmd8_right (h,w,g,x  ,y+1,steps+1),
           mmd8_uright(h,w,g,x-1,y+1,steps+1),
           mmd8_dright(h,w,g,x+1,y+1,steps+1));
}

int mmd8_uleft(int h, int w, int g[h][w], int x, int y, int steps)
{
    if (base_case(h,w,x,y)) return 0;
    putchar('W');
    return max2(g[x][y]?steps:0,
           mmd8_uleft(h,w,g,x-1,y-1,steps+1));
}

int mmd8_uright(int h, int w, int g[h][w], int x, int y, int steps)
{
    if (base_case(h,w,x,y)) return 0;
    putchar('X');
    return max2(g[x][y]?steps:0,
           mmd8_uright(h,w,g,x-1,y+1,steps+1));
}

int mmd8_dleft(int h, int w, int g[h][w], int x, int y, int steps)
{
    if (base_case(h,w,x,y)) return 0;
    putchar('Y');
    return max2(g[x][y]?steps:0,
           mmd8_dleft(h,w,g,x+1,y-1,steps+1));
}

int mmd8_dright(int h, int w, int g[h][w], int x, int y, int steps)
{
    if (base_case(h,w,x,y)) return 0;
    putchar('Z');
    return max2(g[x][y]?steps:0,
           mmd8_dright(h,w,g,x+1,y+1,steps+1));
}

4路解决方案

int mmd4(int h, int w, int g[h][w], int x, int y)
{
    putchar('#');
    return max4(mmd_up   (h,w,g,x-1,y  ,1),
                mmd_down (h,w,g,x+1,y  ,1),
                mmd_left (h,w,g,x  ,y-1,1),
                mmd_right(h,w,g,x  ,y+1,1));
}

int mmd_up(int h, int w, int g[h][w], int x, int y, int steps)
{
    if (base_case(h,w,x,y)) return 0;
    putchar('U');
    return max4(g[x][y]?steps:0,
           mmd_up   (h,w,g,x-1,y  ,steps+1),
           mmd_left (h,w,g,x  ,y-1,steps+1),
           mmd_right(h,w,g,x  ,y+1,steps+1));
}

int mmd_down(int h, int w, int g[h][w], int x, int y, int steps)
{
    if (base_case(h,w,x,y)) return 0;
    putchar('D');
    return max4(g[x][y]?steps:0,
           mmd_down (h,w,g,x+1,y  ,steps+1),
           mmd_left (h,w,g,x  ,y-1,steps+1),
           mmd_right(h,w,g,x  ,y+1,steps+1));
}

int mmd_left(int h, int w, int g[h][w], int x, int y, int steps)
{
    if (base_case(h,w,x,y)) return 0;
    putchar('L');
    return max2(g[x][y]?steps:0,
           mmd_left (h,w,g,x  ,y-1,steps+1));
}

int mmd_right(int h, int w, int g[h][w], int x, int y, int steps)
{
    if (base_case(h,w,x,y)) return 0;
    putchar('R');
    return max2(g[x][y]?steps:0,
           mmd_right(h,w,g,x  ,y+1,steps+1));
}

效用函数

int base_case(int h, int w, int x, int y)
{
    if (x < 0) return 1;
    if (y < 0) return 1;
    if (x >= h) return 1;
    if (y >= w) return 1;
    return 0;
}

int max2(int a, int b)
{
    return ((a > b) ? a : b);
}

int max4(int a, int b, int c, int d)
{
    int m = a;
    if (b > m) m = b;
    if (c > m) m = c;
    if (d > m) m = d;
    return m;
}

int max8(int a, int b, int c, int d, int e, int f, int g, int h)
{
    int m = a;
    if (b > m) m = b;
    if (c > m) m = c;
    if (d > m) m = d;
    if (e > m) m = e;
    if (f > m) m = f;
    if (g > m) m = g;
    if (h > m) m = h;
    return m;
}