2014-01-30 73 views
0

我有以下遞歸方法來創建高度映射山:遞歸方法上的某些分支過早停止

private void createMountain(final float[][] heightMapping, final float startHeight) { 
    boolean[][] traversed = new boolean[width][depth]; 
    boolean positive = (startHeight >= 0f); 
    int x = random.nextInt(width); 
    int z = random.nextInt(depth); 
    recursiveUpdate(heightMapping, traversed, x, z, startHeight, positive); 
} 

private void recursiveUpdate(final float[][] heightMapping, final boolean[][] traversed, final int x, final int z, final float startHeight, final boolean positive) { 
    if (x < 0 || x >= width || z < 0 || z >= depth) { 
     return; 
    } 
    if (traversed[x][z]) { 
     return; 
    } 
    if ((positive && startHeight <= 0f) || (!positive && startHeight >= 0f)) { 
     heightMapping[x][z] = 0f; 
     return; 
    } 
    traversed[x][z] = true; 
    heightMapping[x][z] = startHeight; 
    recursiveUpdate(heightMapping, traversed, x - 1, z - 1, calculateNewStartHeight(startHeight, positive), positive); 
    recursiveUpdate(heightMapping, traversed, x - 1, z + 1, calculateNewStartHeight(startHeight, positive), positive); 
    recursiveUpdate(heightMapping, traversed, x + 1, z - 1, calculateNewStartHeight(startHeight, positive), positive); 
    recursiveUpdate(heightMapping, traversed, x + 1, z + 1, calculateNewStartHeight(startHeight, positive), positive); 
} 

private float calculateNewStartHeight(final float startHeight, final boolean positive) { 
    float delta = random.nextFloat() * maxHeight/maxDecayFactor; 
    return (positive) ? startHeight - delta : startHeight + delta; 
} 

的想法是,它開始於(x, z)然後遞歸地降低周邊小區的值(左下/右下/左上/右上),howevers似乎跳躍單元,通過下面的輸出看到:

0.0 0.5 0.0 0.5 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0  
0.5 0.0 0.9 0.0 0.3 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0  
0.0 1.1 0.0 0.0 0.0 0.3 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0  
1.8 0.0 0.9 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0  
0.0 2.4 0.0 0.8 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0  
3.6 0.0 0.8 0.0 0.9 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0  
0.0 4.4 0.0 1.2 0.0 0.7 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0  
3.5 0.0 2.3 0.0 0.7 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0  
0.0 2.5 0.0 1.1 0.0 0.6 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0  
1.4 0.0 0.4 0.0 0.4 0.0 0.1 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0  
0.0 0.2 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0  
0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0  
0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0  
0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0  
0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0  
0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 

在左邊,你可以看到中間稍高於4.4,而這個問題本身似乎很明顯s,它沒有爲上/下/左/右元素設置任何值,但我認爲我的遞歸已經發現了這個問題。

任何線索?

+0

你試過調試呢? –

+0

@KubaSpatny是的,代碼中沒有'錯誤',這是我的算法中的一些設計缺陷,我無法掌握。 – skiwi

+0

輸出應該是什麼?您在輸出上方的解釋看起來像是在輸出應該的內容。 – mdewitt

回答

1

您不計算頂部,底部,左側和右側的遞歸高度。你只是在計算角落。你只需要添加「非角落」,即。 (x,y)的頂部,底部,左側和右側標記給你的遞歸方法。

private void recursiveUpdate(final float[][] heightMapping, final boolean[][] traversed, 
    final int x, final int z, final float startHeight, final boolean positive) { 
    if (x < 0 || x >= width || z < 0 || z >= depth) { 
     return; 
    } 
    if (traversed[x][z]) { 
     return; 
    } 
    if ((positive && startHeight <= 0f) || (!positive && startHeight >= 0f)) { 
     heightMapping[x][z] = 0f; 
     return; 
    } 

    traversed[x][z] = true; 
    heightMapping[x][z] = startHeight; 
    //This will only calculate the corners of the (x,y point) 
    recursiveUpdate(heightMapping, traversed, x - 1, z - 1, 
        calculateNewStartHeight(startHeight, positive), positive); 
    recursiveUpdate(heightMapping, traversed, x - 1, z + 1, 
        calculateNewStartHeight(startHeight, positive), positive); 
    recursiveUpdate(heightMapping, traversed, x + 1, z - 1, 
        calculateNewStartHeight(startHeight, positive), positive); 
    recursiveUpdate(heightMapping, traversed, x + 1, z + 1, 
        calculateNewStartHeight(startHeight, positive), positive); 

    //Add top, bottom, left and right indicies for (x,y) 
    //bottom 
    recursiveUpdate(heightMapping, traversed, x, z - 1, 
        calculateNewStartHeight(startHeight, positive), positive); 
    //top 
    recursiveUpdate(heightMapping, traversed, x, z + 1, 
        calculateNewStartHeight(startHeight, positive), positive); 
    //right 
    recursiveUpdate(heightMapping, traversed, x + 1, z, 
        calculateNewStartHeight(startHeight, positive), positive); 
    //left 
    recursiveUpdate(heightMapping, traversed, x - 1, z, 
        calculateNewStartHeight(startHeight, positive), positive); 
} 
+1

謝謝,這確實解決了它,甚至通過在頂部/下部/左側/右側遞歸來實現'優化',這實際上最初是我的想法。 – skiwi