2013年7月20日

Array 陣列型態

Arrays 陣列
PHP的Array實際上是一個有序的映射。
映射是一種把values關連到keys的類型。

它可以被當作陣列、列表(list)、向量(vector)、雜湊表(hash table)(是映射的一種實現)、字典(dictionary)、集合(collection)、堆疊(stack), 序列(queue)以及其他更多的可能。

語法
array(
key => value
, ......
,key2 => value2
,key3 => value3
)
鍵(key)可以是一個整數或字串。
值(value)可以是任何型態。

最後一個元素之後的逗號可以省略。即使加上逗號,在計算陣列元素上不會造成影響。
<?php
// 最後一個沒加上逗號
$a = array(1, 2);
echo count($a);  // 2
 
// 最後一個加上逗號
$a = array(1, 2, );
echo count($a);  // 2
?>

自PHP5.4起可以使用簡單定義語法,用[]取代array()。
<?php
$array = array(
    "foo" => "bar",
    "bar" => "foo",
);
 
// 自 PHP 5.4 起
$array = [
    "foo" => "bar",
    "bar" => "foo",
];
?>

Key會有下列提到的強制轉換
1. 包含有合法整數型態的字串值會被轉換為整數型態。例如字串"8"實際會被儲存為整數8。但是"08"則不會被強制轉換,因為不是一個合法的十進位數值。
2. 浮點數會被轉換為整數,小數點部分無條件捨去。例如8.7會被儲存為8。
3. 布林值會被轉換成整數,true會儲存為1,false會被儲存為0。
4. Null會被轉換成空字串,null會被儲存為""。
5. 陣列和物件不能被當作key。如果使用會出現警告Illegal offset type。

注意事項
1. 一個陣列中多個元素使用同一個鍵,則後者會覆蓋前者。
2. 陣列中可以同時擁有字串以及整術類型的鍵。
3. 如果陣列沒有指定鍵,則取當前最大的整數索引值,新的鍵則是該值加一。
4. 如果指定的鍵已經有值,則該值會被覆蓋。
5. 可以只對某些元素指定鍵,其他元素不指定。
6. 取當前最大的整數索引值是指曾經存在過即可。

讀取陣列元素
透過array[key]或者array{key}

Note:試著讀取一個未定義的陣列索引與讀取任何未定義的變數一樣,會導致E_NOTICE等級的錯誤訊息,其結果為NULL。

用[]的語法新增或修改陣列
1. 直接指定該陣列內的key-value,$array[key] = value
2. 利用[]新增一個元素到陣列內,$array[] = value

第二種方法如果陣列不存在則會新建一個。但是不建議使用該方式來新建陣列。初始化變數的最好方式是直接給值。

用unset和鍵刪除某個元素
unset($array[key])

為什麼$foo[bar]錯了?
當你使用這樣的方式存取一個元素時,會出現一個E_NOTICE的錯誤訊息(Notice: Use of undefined constant name - assumed 'foo'),但是程式還是可以正常運作,那是因為PHP先試著尋找一個定義為foo的常數,找不到的時候將foo自動轉換成字串"foo"並使用它。

Note:但是這不代表你總是要將鍵加上引號。如果鍵是一個常數或變數則不需要。

轉換為陣列
對於任意整數類型、浮點數類型、字串類型、布林類型和資源類型,如果將其轉換為陣列,將得到一個僅有一個元素的陣列,其鍵為0,該元素的值為原來的值。

將物件轉換為陣列,則結果為一個陣列,其元素為該物件的屬性,鍵將為屬性變數名稱。但是有幾點要注意,整數屬性不可讀取,私有屬性前面會加上類別名稱作為前綴字,保護屬性前面會加上"*"作為前綴字。這些前綴字的前後都各有一個NULL字元,這會導致一些不可預期的行為。
<?php
// 整數屬性不可讀取
$obj = new stdClass();
$obj->{111} = 222;
var_dump($obj);
 
$arr = (array)$sobj;
var_dump($arr);
 
echo $arr[111]; // 產生 Notice: Undefined offset: 111 錯誤
echo $arr["111"]; // 產生 Notice: Undefined offset: 111 錯誤
?>

下面的例子印出後會看到兩個鍵為AA,但是實際上其中一個是"\0A\0A"。
<?php
class A {
    private $A; // This will become 'AA'
}
 
class B extends A {
    private $A; // This will become 'BA'
    public $AA; // This will become 'AA'
}
var_dump((array) new B());
?>
將NULL轉換陣列會得到一個空陣列。

比較陣列
可以用array_diff()陣列運算子來比較陣列。

直接改變陣列的值自PHP5開始可以透過參照傳遞做到。之前的版本需要採取變通的方法。
注意當使用此方法,該變數可能會影響到原有陣列。
<?php
// PHP 5
foreach ($colors as &$color) {
    $color = strtoupper($color);
}
unset($color); /* ensure that following writes to
$color will not modify the last array element */
 
// Workaround for older versions
foreach ($colors as $key => $color) {
    $colors[$key] = strtoupper($color);
}
 
print_r($colors);
?>

沒有留言:

張貼留言