微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

如何转换为尾递归

如何解决如何转换为尾递归

我了解尾递归是什么,但我无法将此方法转换为尾递归。我正在尝试计算矩阵中有多少相邻元素。因此,我的问题是如何将其转化为尾递归?

public static int ExploreAndLabelColony(char[][] grid,int i,int j,char c,int count) { 
        grid[i][j] = c;
        count = 1;
        if ((i>0 && i<grid.length && j<grid[0].length) && (grid[i-1][j] == '1')) { //vertical bottom
            count +=ExploreAndLabelColony(grid,i-1,j,c,count); 
            }
        if (i+1<grid.length && j<grid[0].length && grid[i+1][j] == '1') { //vertical top
            count+=ExploreAndLabelColony(grid,i+1,count); 
            }
        if (j>0 && i<grid.length && j<grid[0].length && grid[i][j-1] == '1') { //horizontal left
            count +=ExploreAndLabelColony(grid,i,j-1,count); 
            }
        if (i<grid.length && j+1<grid[0].length && grid[i][j+1] == '1') { //horizontal right
            count+=ExploreAndLabelColony(grid,j+1,count); 
            }
        if (i+1<grid.length && j+1<grid[0].length && grid[i+1][j+1] == '1') { //diagonal bottom right
            count+=ExploreAndLabelColony(grid,count);
            } 
        if (j>0 && i+1<grid.length && j<grid[0].length && grid[i+1][j-1] == '1') { //diagonal bottom right
            count+=ExploreAndLabelColony(grid,count);
            } 
        if (i>0 && i<grid.length && j+1<grid[0].length && grid[i-1][j+1] == '1') { //diagonal top right
            count+=ExploreAndLabelColony(grid,count);
            } 
        if (i>0 && j>0 && i<grid.length && j<grid[0].length && grid[i-1][j-1] == '1') { //diagonal top left
            count+=ExploreAndLabelColony(grid,count);
            }
            
        return count;
    }

解决方法

这可能符合尾递归:

static class Queue {
    int i;
    int j;
    Queue next;
    Queue(int i,int j,Queue next) {
        this.i = i;
        this.j = j;
        this.next = next;
    }
}

int exploreAndLabel(char[][] grid,int i,char c) {
    return exploreAndLabel(new Queue(i,j,null),grid,c,0);
}

int exploreAndLabel(Queue queue,char[][] grid,char c,int count) {
    if (queue == null) {
        return count; // no more work
    }
    int i = queue.i;
    int j = queue.j;
    queue = queue.next;
    if (i < 0 || j < 0 || i >= grid.length || j >= grid[0].length) {
        // outside grid
    } else if (grid[i][j] != '1') {
        // outside colony
    } else {
        grid[i][j] = c;  // label
        count++;
        queue = new Queue(i - 1,j - 1,queue);
        queue = new Queue(i - 1,j + 1,queue);
        queue = new Queue(i,queue);
        queue = new Queue(i + 1,queue);
    }
    return exploreAndLabel(queue,count);
}

这是一个测试:

@Test
public void testTailRecursion() {
    char[][] grid = Stream.of(
            "00000101","00001101","00111010")
            .map(String::toCharArray)
            .toArray(char[][]::new);

    int count = exploreAndLabel(grid,2,3,'2');
    Assert.assertEquals(9,count);
}

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。