2012-08-16 65 views
2

我正在使用鋸齒陣列在我正在製作的遊戲中保存地圖段(集羣)。數組中的位置對應於地圖中簇的位置。此外,如果內部數組(鋸齒形部分)不再有任何集羣加載(集羣在未使用超時後從陣列中移除),那麼外部數組的該元素將設置爲空以保持地圖的內存使用情況下。c#鋸齒陣列錯誤(元素不總是設置)

問題隨機看似出現時,遊戲將嘗試從地圖上羣集:

public Cluster getCluster(int xIndex, int yIndex) 
{ 
    lock (xAxis) 
    { 
     loadCluster(xIndex, yIndex); 
     return xAxis[xIndex][yIndex]; 
    } 
} 

public void loadCluster(int xIndex, int yIndex) 
{ 
    lock (xAxis) 
    { 
     if (xAxis[xIndex] == null) 
      xAxis[xIndex] = new Cluster[(int)worldSize.Y]; 
     if (xAxis[xIndex][yIndex] == null) 
      xAxis[xIndex][yIndex] = new Cluster(this, new Vector2(xIndex * 256, yIndex * 256), worldLoader.loadClusterData(xIndex, yIndex)); 
    } 
} 

loadCluster(int, int)方法應該確保羣集被加載到陣列的getCluster(int, int)方法檢索以及幾乎所有前它的時間,但偶爾loadCluster(int, int)以某種方式無法添加羣集。

它似乎並不與任何特定集羣發生,但總是發生在內部陣列尚未添加(但是,大部分時間它創建沒有問題,在所有內部陣列)。另外,當Visual Studio捕捉到隨後發生的空指針異常時,回退並重新調用loadCluster(int, int)總是(至少目前爲止)如常工作。在getCluster(int, int)方法中向loadCluster(int, int)添加額外的呼叫也大大降低了此錯誤的頻率。

老實說,我不知道是什麼,甚至導致這相當簡單功能到不行,看似隨意。任何幫助,將不勝感激

編輯:其他的代碼編輯X軸[] []

public override void Update(GameTime gameTime) 
{ 
    for (int x = 0; x < worldSize.X; x++) 
    { 
     if (xAxis[x] == null) continue; 
     int loaded = 0; 
     for (int y = 0; y < worldSize.Y; y++) 
     { 
      if (xAxis[x][y] == null) 
      { 
       continue; 
      } 
      xAxis[x][y].Update(gameTime); 

      if (xAxis[x][y].clusterLoaded) 
      { 
       loaded++; 
      } 
      else if (xAxis[x][y].clusterTimer == 0) 
      { 
       xAxis[x][y] = null; 
      } 
     } 

     if(loaded == 0) xAxis[x] = null; 
    } 
} 

Cluster.clusterLoaded是一個布爾表示如果羣集正在使用中。 Cluster.clusterTimer是一個整數,一旦clusterLoaded變爲false就會倒計時。如果clusterLoaded再次變爲真,則將其重置爲最大值。每運行Cluster.Update(GameTime)運行時減1,而clusterLoaded爲假。 loaded用於計算當前內部數組中的多少羣集被加載。

+0

沒有確保(int)worldSize.Y> yIndex的代碼。請添加這樣的斷言,以便在這種情況下打破。 – Artak 2012-08-16 22:09:18

+0

你可以發佈所有更改數組的代碼,包括從它移除的位 - 清理等。 – 2012-08-16 22:10:14

+0

看起來很棒,但目前代碼的其他部分確保yIndex永遠不會比worldSize.Y更大。儘管我會添加一張支票。無論如何,即使xIndex和yIndex都在數組範圍內,也會發生錯誤。 – Kalia 2012-08-16 22:11:52

回答

3

改變這裏的第一件事就是修改loadCluster方法直接從它返回x軸[xIndex] [yIndex]值。那麼就不需要鎖定getCluster方法。 代碼的其他部分呢 - 從描述來看,它似乎是一個多線程問題。雖然你已經鎖定了xAxis變量,但我不知道你在別的地方做了什麼。 還有一點 - 語言中的數組實際上是一個核心功能,所以在那裏出現錯誤(我的意思是微軟)確實是意外的。

+0

loadCluster只加載和不返回任何東西是故意的,我可能會使它私人/保護。但是,你的多線程點很有趣。我有一個BackgroundWorker,它會生成一個實時小地圖並可能會產生干擾。我會給它一些測試。 – Kalia 2012-08-16 22:28:13

+0

啊哈。它確實看起來是一個線程問題。取消激活BackgroundWorker可防止發生錯誤。我也設法找到問題的根源。我沒有鎖定Update方法,所以BackgroundWorker必須在那裏搞點東西。非常感謝! – Kalia 2012-08-16 22:39:23

+0

不客氣。很高興幫助。 – Artak 2012-08-18 15:20:34