小編給大家分享一下php中向數(shù)組追加元素的方法有哪些,相信大部分人都還不怎么了解,因此分享這篇文章給大家參考一下,希望大家閱讀完這篇文章后大有收獲,下面讓我們一起去了解一下吧!
創(chuàng)新互聯(lián)專注為客戶提供全方位的互聯(lián)網(wǎng)綜合服務(wù),包含不限于網(wǎng)站制作、網(wǎng)站設(shè)計(jì)、新縣網(wǎng)絡(luò)推廣、微信小程序開發(fā)、新縣網(wǎng)絡(luò)營(yíng)銷、新縣企業(yè)策劃、新縣品牌公關(guān)、搜索引擎seo、人物專訪、企業(yè)宣傳片、企業(yè)代運(yùn)營(yíng)等,從售前售中售后,我們都將竭誠(chéng)為您服務(wù),您的肯定,是我們最大的嘉獎(jiǎng);創(chuàng)新互聯(lián)為所有大學(xué)生創(chuàng)業(yè)者提供新縣建站搭建服務(wù),24小時(shí)服務(wù)熱線:18980820575,官方網(wǎng)址:www.cdcxhl.com
向數(shù)組追加元素
我們知道 php 在數(shù)組棧尾追加元素的方式有兩種
$a = []; array_push($a,'test'); $a[] = 'test';
那么這兩種方式有什么區(qū)別呢?
我們先來比較一下性能
ArrayPush 一個(gè) ArrayPush 類 pushEachOne() 循環(huán)體中使用 array_push() 來為 $a 追加元素 pushEachTwo() 循環(huán)體中使用 $a[] = $var 來為 $a 追加元素 /** * Class ArrayPush */ class ArrayPush { /** * @param int $times * @return array */ public static function pushEachOne(int $times): array { $a = []; $b = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]; for ($i = 0; $i < $times; $i++) { array_push($a, $b[$i % 10]); } return $a; } /** * @param int $times * @return array */ public static function pushEachTwo(int $times): array { $a = []; $b = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]; for ($i = 0; $i < $times; $i++) { $a[] = $b[$i % 10]; } return $a; } }
編寫代碼測(cè)試
循環(huán)追加 100 萬個(gè)元素
ini_set('memory_limit', '4000M'); $timeOne = microtime(true); $a = ArrayPush::pushEachOne(1000000); echo 'count pushEachOne result | ' . count($a) . PHP_EOL; $timeTwo = microtime(true); $b = ArrayPush::pushEachTwo(1000000); echo 'count pushEachTwo result | ' . count($b) . PHP_EOL; $timeThree = microtime(true); echo PHP_EOL; echo 'pushEachOne | ' . ($timeTwo - $timeOne) . PHP_EOL; echo 'pushEachTwo | ' . ($timeThree - $timeTwo) . PHP_EOL; echo PHP_EOL;
結(jié)果
結(jié)果不言而喻,$a[] = 比使用 array_push() 快了接近三倍
count pushEachOne result | 1000000 count pushEachTwo result | 1000000 pushEachOne | 1.757071018219 pushEachTwo | 0.67165303230286
分析
array_push () 為什么慢?這么慢,我們還有使用它的場(chǎng)景嗎?
官方手冊(cè)
array_push — 將一個(gè)或多個(gè)單元壓入數(shù)組的末尾(入棧) array_push ( array &$array , mixed $value1 [, mixed $... ] ) : int array_push() 將 array 當(dāng)成一個(gè)棧,并將傳入的變量壓入 array 的末尾。array 的長(zhǎng)度將根據(jù)入棧變量的數(shù)目增加。和如下效果相同:
并對(duì)每個(gè)傳入的值重復(fù)以上動(dòng)作。
● Note: 如果用 array_push() 來給數(shù)組增加一個(gè)單元,還不如用 \$array[] = ,因?yàn)檫@樣沒有調(diào)用函數(shù)的額外負(fù)擔(dān)。
● Note: 如果第一個(gè)參數(shù)不是數(shù)組,array_push() 將發(fā)出一條警告。這和 \$var[] 的行為不同,后者會(huì)新建一個(gè)數(shù)組。
官方源碼
看一下源碼中的 array_push()
/* {{{ proto int array_push(array stack, mixed var [, mixed ...]) Pushes elements onto the end of the array */ PHP_FUNCTION(array_push) { zval *args, /* Function arguments array */ *stack, /* Input array */ new_var; /* Variable to be pushed */ int i, /* Loop counter */ argc; /* Number of function arguments */ //這一段是函數(shù)的參數(shù)解析 ZEND_PARSE_PARAMETERS_START(2, -1) Z_PARAM_ARRAY_EX(stack, 0, 1) Z_PARAM_VARIADIC('+', args, argc) ZEND_PARSE_PARAMETERS_END(); /* For each subsequent argument, make it a reference, increase refcount, and add it to the end of the array */ for (i = 0; i < argc; i++) { //拷貝一個(gè) ZVAL_COPY(&new_var, &args[i]); //插入新數(shù)值,自動(dòng) if (zend_hash_next_index_insert(Z_ARRVAL_P(stack), &new_var) == NULL) { if (Z_REFCOUNTED(new_var)) Z_DELREF(new_var); php_error_docref(NULL, E_WARNING, "Cannot add element to the array as the next element is already occupied"); RETURN_FALSE; } } /* Clean up and return the number of values in the stack */ RETVAL_LONG(zend_hash_num_elements(Z_ARRVAL_P(stack))); } /* }}} */
$a[] = 的實(shí)現(xiàn)是根據(jù)賦值的變量類型調(diào)用了一系列 Zend_API 函數(shù) add_next_index_* ,它們?cè)谠O(shè)置一個(gè)對(duì)應(yīng)類型的 zval 值以后直接調(diào)用了 zend_hash_next_index_insert
ZEND_API int add_next_index_long(zval *arg, zend_long n) /* {{{ */ { zval tmp; ZVAL_LONG(&tmp, n); return zend_hash_next_index_insert(Z_ARRVAL_P(arg), &tmp) ? SUCCESS : FAILURE; } /* }}} */ ZEND_API int add_next_index_null(zval *arg) /* {{{ */ { zval tmp; ZVAL_NULL(&tmp); return zend_hash_next_index_insert(Z_ARRVAL_P(arg), &tmp) ? SUCCESS : FAILURE; } /* }}} */ ZEND_API int add_next_index_bool(zval *arg, int b) /* {{{ */ { zval tmp; ZVAL_BOOL(&tmp, b); return zend_hash_next_index_insert(Z_ARRVAL_P(arg), &tmp) ? SUCCESS : FAILURE; } /* }}} */ ZEND_API int add_next_index_resource(zval *arg, zend_resource *r) /* {{{ */ { zval tmp; ZVAL_RES(&tmp, r); return zend_hash_next_index_insert(Z_ARRVAL_P(arg), &tmp) ? SUCCESS : FAILURE; } /* }}} */ ZEND_API int add_next_index_double(zval *arg, double d) /* {{{ */ { zval tmp; ZVAL_DOUBLE(&tmp, d); return zend_hash_next_index_insert(Z_ARRVAL_P(arg), &tmp) ? SUCCESS : FAILURE; } /* }}} */ ZEND_API int add_next_index_str(zval *arg, zend_string *str) /* {{{ */ { zval tmp; ZVAL_STR(&tmp, str); return zend_hash_next_index_insert(Z_ARRVAL_P(arg), &tmp) ? SUCCESS : FAILURE; } /* }}} */ ZEND_API int add_next_index_string(zval *arg, const char *str) /* {{{ */ { zval tmp; ZVAL_STRING(&tmp, str); return zend_hash_next_index_insert(Z_ARRVAL_P(arg), &tmp) ? SUCCESS : FAILURE; } /* }}} */ ZEND_API int add_next_index_stringl(zval *arg, const char *str, size_t length) /* {{{ */ { zval tmp; ZVAL_STRINGL(&tmp, str, length); return zend_hash_next_index_insert(Z_ARRVAL_P(arg), &tmp) ? SUCCESS : FAILURE; } /* }}} */ ZEND_API int add_next_index_zval(zval *arg, zval *value) /* {{{ */ { return zend_hash_next_index_insert(Z_ARRVAL_P(arg), value) ? SUCCESS : FAILURE; } /* }}} */
總結(jié)
經(jīng)過上面的分析,仿佛 array_push() 沒有任何存在的意義,真的是這樣嗎?
● 一般情況下,array_push() 性能太差,所以我們應(yīng)當(dāng)使用 $array[] = 來替換掉它
● 如果一次追加多個(gè)單元,使用 array_push()
以上是php中向數(shù)組追加元素的方法有哪些的所有內(nèi)容,感謝各位的閱讀!相信大家都有了一定的了解,希望分享的內(nèi)容對(duì)大家有所幫助,如果還想學(xué)習(xí)更多知識(shí),歡迎關(guān)注創(chuàng)新互聯(lián)行業(yè)資訊頻道!