2016-03-27 16 views
2

JSからJavaへの書き換えコードを試しています。コードはDiamond squareアルゴリズムです。ダイヤモンドスクエアアルゴリズムが機能しません(JSからJAVAへのコードの書き換え)

ソースは次のとおりです。http://www.playfuljs.com/realistic-terrain-in-130-lines/

私はコードを書き換えるが、私のコードは動作していない...

出力が悪いです。 Java

私のコードは次のとおりです。

public class MapGenerator { 

    public static void main(String[] args) { 
     MapGenerator mg = new MapGenerator(9); 
     mg.generate(); 
     mg.printMap(); 
    } 

    private int size, max; 
    double[] map; 
    int[][] matrix; 

    public MapGenerator(int detail) { 
     this.size = (int) Math.pow(2, detail) + 1; 
     this.max = this.size - 1; 
     this.map = new double[this.size * this.size]; 
    } 

    private double get(int x, int y) { 
     if (x < 0 || x > this.max || y < 0 || y > this.max) { 
      return -1; 
     } 
     return this.map[x + this.size * y]; 
    } 

    private void set(int x, int y, double val) { 
     this.map[x + this.size * y] = val; 
    } 

    public void generate() { 
     set(0, 0, max); 
     set(this.max, 0, max/2); 
     set(this.max, this.max, 0); 
     set(0, this.max, max/2); 
     divide(this.max); 

     buildMatrix(); 
     saveTerrain(0, 0, 0, 0, matrix, "vystup.ter"); 
    } 

    private void buildMatrix() { 
     matrix = new int[size][size]; 

     for (int i = 0; i < matrix.length; i++) { 
      for (int j = 0; j < matrix[0].length; j++) { 
       matrix[i][j] = (int) map[i + j]; 
      } 
     } 

    } 

    private void divide(int size) { 
     //? 
     double roughness = 0.7; 

     int x, y, half = size/2; 
     double scale = roughness * size; 

     if (half < 1) { 
      return; 
     } 
     for (y = half; y < max; y += size) { 
      for (x = half; x < max; x += size) { 
       square(x, y, half, Library.randInt(0, 100) * scale * 2 - scale); 
      } 
     } 
     for (y = 0; y <= max; y += half) { 
      for (x = (y + half) % size; x <= max; x += size) { 
       diamond(x, y, half, Library.randInt(0, 100) * scale * 2 - scale); 
      } 
     } 
     divide(size/2); 
    } 

    private void square(int x, int y, int size, double offset) { 

     double tmp_1 = get(x, y - size); // top 
     double tmp_2 = get(x + size, y);  // right 
     double tmp_3 = get(x, y + size);  // bottom 
     double tmp_4 = get(x - size, y);  // left 

     set(x, y, ((tmp_1 + tmp_2 + tmp_3 + tmp_4)/4.0) + offset); 
    } 

    private void diamond(int x, int y, int size, double offset) { 
     double tmp_1 = get(x, y - size);  // top 
     double tmp_2 = get(x + size, y);  // right 
     double tmp_3 = get(x, y + size);  // bottom 
     double tmp_4 = get(x - size, y);  // left 

     set(x, y, ((tmp_1 + tmp_2 + tmp_3 + tmp_4)/4.0) + offset); 
    } 

    public void printMap() { 
     for (int i = 0; i < matrix.length; i++) { 
      for (int j = 0; j < matrix[0].length; j++) { 
       System.out.print(matrix[i][j] + " "); 
      } 
      System.out.println(""); 
     } 
    } 

    public void saveTerrain(int canonX, int canonY, int targetX, int targetY, 
      int[][] terrain, String fName) { 
     int height = terrain.length; 
     int width = terrain[0].length; 

     DataOutputStream fout = null; 
     try { 
      // Samotný zápis dat 
      fout = new DataOutputStream(new FileOutputStream(fName)); 

      fout.writeInt(width); 
      fout.writeInt(height); 
      fout.writeInt(canonX); 
      fout.writeInt(canonY); 
      fout.writeInt(targetX); 
      fout.writeInt(targetY); 

      for (int y = 0; y < height; ++y) { 
       for (int x = 0; x < width; ++x) { 
        fout.writeInt(terrain[y][x]); 
       } 
      } 
     } /* 
     * Následuje pouze zavření souboru a ošetrení výjimek 
     */ catch (FileNotFoundException e) { 
      System.err.println("Nepovedlo se otevrit vystupni soubor."); 
     } catch (IOException e) { 
      System.err.println("Nepovedlo se zapsat vystupni soubor."); 
     } finally { 
      try { 
       if (fout != null) { 
        fout.close(); 
       } 
      } catch (IOException e) { 
       System.err.println("Nepovedlo se uzavrit vystupni soubor."); 
      } 
     } 
    } 
} 

誰も私を助けることができますか?アルゴの

出力は、出力の

視覚化..私がイメージに他のプログラムを使用して可視化するint[][]次のとおりです。

OUTPUT IMAGE LINK

そして、これは、それがどのように見えるべきかである

OUTPUT IMAGE LINK

エラーは発生していませんが、出力が間違っています。 ありがとうございました。

+0

コンパイルエラーが発生していますか?期待される成果とは何ですか?あなたの質問にすべてを含めてください。誰もが想定していることを理解するために100行のコード行をデバッグすることはありません。 – user2004685

+0

エラーは出ませんが、出力が間違っています – drefraew

+0

期待どおりの出力が得られますか? –

答えて

0

私は同じソースから昨日同じコードをコーディングしていました。再帰的なアプローチは、同じステップで細分化された領域と不規則性の四角形のステップオーバーラップのために本当に難しいです。だから私は、私が130行から50行程度コメントしているのがわかるように、これを反復的な方法で(ゼロにすることで/プログラミング環境でスタックが壊れるのでずっと速く)行うことにしました。

これは私がC++に(非再帰的に)それを行う方法です。

void diamond_square(int size) 
    { 
    picture pic; 
    int x,y,xx,yy,xs,ys,d,d2,r; 
    for (xs=1;xs<size;xs<<=1); xs>>=1; ys=xs; // align to power of 2 
    pic.resize(xs+1,ys+1); pic.pf=_pf_u;  // resize image to power of 2 +1 
    d=xs; d2=d>>1; r=128;      // init step,half step and randomness 
    Randomize(); 
    pic.p[ 0][ 0].dd=r;       // set corners values (should be random but I want this) 
    pic.p[ 0][xs].dd=r; 
    pic.p[ys][ 0].dd=r; 
    pic.p[ys][xs].dd=r; 
    for (;d2;d=d2,d2>>=1)      // subdivide step until full image is filled 
     { 
     // diamond 
     for (y=d2,yy=ys-d2;y<=yy;y+=d) 
     for (x=d2,xx=xs-d2;x<=xx;x+=d) 
      pic.p[y][x].dd=((pic.p[y-d2][x-d2].dd+pic.p[y-d2][x+d2].dd+pic.p[y+d2][x-d2].dd+pic.p[y+d2][x+d2].dd)>>2)+Random(r); 
     // square 
     for (y=d2,yy=ys-d2;y<=yy;y+=d) 
     for (x=d ,xx=xs-d ;x<=xx;x+=d) 
      pic.p[y][x].dd=((pic.p[y][x-d2].dd+pic.p[y][x+d2].dd+pic.p[y-d2][x].dd+pic.p[y+d2][x].dd)>>2)+Random(r); 
     for (y=d ,yy=ys-d ;y<=yy;y+=d) 
     for (x=d2,xx=xs-d2;x<=xx;x+=d) 
      pic.p[y][x].dd=((pic.p[y][x-d2].dd+pic.p[y][x+d2].dd+pic.p[y-d2][x].dd+pic.p[y+d2][x].dd)>>2)+Random(r); 
     for (x=d2,xx=xs-d2;x<=xx;x+=d) 
      { 
      y= 0; pic.p[y][x].dd=((pic.p[y][x-d2].dd+pic.p[y][x+d2].dd+pic.p[y+d2][x].dd)/3)+Random(r); 
      y=ys; pic.p[y][x].dd=((pic.p[y][x-d2].dd+pic.p[y][x+d2].dd+pic.p[y-d2][x].dd)/3)+Random(r); 
      } 
     for (y=d2,yy=ys-d2;y<=yy;y+=d) 
      { 
      x= 0; pic.p[y][x].dd=((pic.p[y][x+d2].dd+pic.p[y-d2][x].dd+pic.p[y+d2][x].dd)/3)+Random(r); 
      x=xs; pic.p[y][x].dd=((pic.p[y][x-d2].dd+pic.p[y-d2][x].dd+pic.p[y+d2][x].dd)/3)+Random(r); 
      } 
     // adjust randomness 
     r=(r*220)>>8; if (r<2) r=2; 
     } 
    // here pic holds the terrain map 
    } 

私はここにいくつかのメンバー私自身pictureクラスを使用します。

  • resize(xs,ys)を新しい解像度
  • に画像のサイズを変更
  • p[ys][xs].ddは、32個の符号なし整数の形のピクセルアクセスですDWORD
  • pfは、ピクセル形式である。これは、あなたが行動を変えるためにr初期ランダムと調整値で遊ぶことができますdiamond_square(513);

    example

    ための結果である

(あなたはこれを無視することができます)。また、最初のコーナー値を変更することもできます。

私のプログラムのローカルのint xs,ys変数は、2 + 1のパワーではなく2の値のパワーを保持していることに注意してください。

関連する問題