2009-12-23 78 views
2

我有一個函數,它必須接受一個點數組或一個點數組(一個2或3維數組)的數組。我正在尋找一種可靠的方法來檢測它是否有2或3級。關鍵是,我不能指望在陣列上的按鍵做檢查,所以這不會工作:如何正確計算數組中的級別數量?

$levels = isset($array[0][0]) && is_array($array[0][0]) ? 3 : 2; 

..as第一關鍵可能不是0它通常是,但我不我不想依賴這個。無論如何,這是一個蹩腳的和非常謹慎的方式來做到這一點。最好,我想檢查任何數量的水平沒有必須遍歷整個陣列。

這裏的陣列可能是什麼樣子:

array(5) { 
    [2] => array(2) { 
     [x] => 3 
     [y] => 6 
    } 
    [3] => array(2) { 
     [x] => 4 
     [y] => 8 
    } 
    ... 

和三維陣列將包含這些陣列。

一些注意事項:

  • 數組是很大,所以通過陣列完全循環是不是一個很好的選擇
  • 的陣列數字和順序索引(與最後一個級別的例外,已經x和y)
  • 數組鍵可能會或可能不會從0

在寫這開始,我提出了這可能是可行的解決方案;一個遞歸函數,檢查數組的第一項,如果是,則調用它自己的新發現數組等。

有沒有更好的,更清晰的想法?用於支持可能同時具有標量值和數組的數組的附加點(例如,數組的第一項可能是字符串,但下一個是數組)。

+0

我不認爲有任何其他方式,因爲PHP數組實際上是作爲樹實現的,而不是數組,所以它不知道數組中有多少「層」。 – 2009-12-23 07:53:39

回答

5

如果你期待一個完整的一個或多個陣列的一個完整的數組,那麼你可以嘗試: -

if (isset $points[0][0][0]) 

但是,如果你的數組稀疏,那麼它更難。 基本的問題是,一個PHP「數組」實際上是一維散列。訣竅是一個值可以是另一個「數組」。所以你需要訪問第二級來確定它是一個值還是一個數組。

再次,如果你期望一個給定的數組只包含點值,或者你只需​​要檢查一個條目,只有其他陣列:

if (is_array(current(current($points)))) 

應該得到你想要的一切:電流()函數返回當前的數組指針(默認爲第一個 - 所以它總是會被設置爲某個東西),所以內部當前($ points)會給你$ points [0]或者第一個入口帶有實際值,外部電流會讓你獲得類似於$ points [0] [0]的東西。

+0

當前(當前($分))解決方案適用於這種情況,所以我會使用它。至少它比我想象中的任何東西都乾淨,它也適用於具有未知開始鍵的陣列。謝謝! – 2009-12-23 08:59:55

1

我沒有看到你怎麼能做到這一點,至少沒有通過數組迭代。簡單的事實是,數組中的任何一個元素都可以有一個額外的級別。因此,每個元素都需要進行測試。

話雖這麼說,你仍然可以使用遞歸來提高你的代碼位:

/** 
* Determine the maximum depth of an array. 
* @param $input The object to test. Might be an array, or might be an int (or 
*  any other object). 
* @param $startDepth The starting depth. Will be added as an offset to the 
*  result. 
* @return The depth of the array, plus any initial offset specified in 
*   $startDepth. 
*/ 
function testDepth($input, $startDepth = 0) { 
    if (is_array($input) { 
     $max = $startDepth; 
     for ($array as $i) { 
      // Check what the depth of the given element is 
      $result = testDepth($i, $startDepth + 1); 
      // We only care about the maximum value 
      if ($result > $max) { 
       $max = $result; 
      } 
     } 
     return $max; 
    } else { 
     // This isn't an array, so it's assumed not to be a container. 
     // This doesn't add any depth to the parent array, so just return $startDepth 
     return $startDepth; 
    } 
} 

testDepth($array); 
+0

在PHP中沒有這樣的構造: ($ array as $ i){ 你測試了你的代碼嗎? – mrarm 2015-11-17 07:44:41

1

$ levels = is_array(current(current($ array)))? 3:2;