How to find the next numeric index of an existing array?
I'm looking for a simple way to obtain the next numerical index of an array for a new element that would have been chosen by PHP as well.
Example 1:
$array = array();
$array[] = 'new index';
This would be 0 for this case.
Example 1a:
$array = array(100 => 'prefill 1');
unset($x[100]);
$x[] = 'new index';
This would be 101 for this case.
Example 2:
$array = array(-2 => 'prefill 1' );
$array[] = 'new index';
This would be 0 again for this case.
Example 3:
$array = array(-2 => 'prefill 1', 1 => 'prefill 2' );
$array[] = 'new index';
This would be 2 for this case.
I'd like now to know the next numerical key that PHP would have chosen as well for the new element in the array but w/o iterating over all the arrays values if possible.
I need this for a own array implementation via the SPL that should mimic PHP default behavior if a new element is added w/o specifying the offset.
Example 4:
$array = array(-2 => 'prefill 1', 'str-key-1' => 'prefill 2', 1 => 'prefill 3' , 'str-key-2' => 'prefill 4');
$array[] = 'new index';
This would be 2 for this case again.
Example 5:
$array = array(-2 => 'prefill-1', 'str-key-1' => 'prefill-2', 1 => 'prefill-3' , '5667 str-key-2' => 'prefill-4');
$array[] = 'new index';
This would be 2 for this case as well.
Update: I've added more examples t开发者_开发问答o show some of the edge cases.
Method 1:
Use end
to advance the array to the end. The get the key
of that item. Finally, add 1 to it to get the index of next item. Like this:
$array [ ] = 'I';
$array [4] = 'Like';
$array [ ] = 'Turtles';
end($array);
$last = key($array);
$nextindex = $last + 1;
echo $nextindex;
This outputs:
6
This method fails in cases where last index is not greatest or a string (as pointed out in comments). So, there is this better method 2 in those cases.
Method 2:
This method works on negative and string based indexes:
You can get array_keys
and do a max
of it, then +1
. Like this:
$array = array(-2 => 'prefill 1', 'str-key-1' => 'prefill 2', 1 => 'prefill 3' , 'str-key-2' => 'prefill 4');
echo max(array_keys($array)) + 1;
This outputs correctly:
2
A zend hash table has an element nNextFreeElement
, which contains the number you are looking for. Every time an item is added, this field is updated to be the maximum of itself and the index + 1.
ZEND_API int _zend_hash_index_update_or_next_insert(HashTable *ht, ulong h, void *pData, uint nDataSize, void **pDest, int flag ZEND_FILE_LINE_DC)
{
...
if ((long)h >= (long)ht->nNextFreeElement) {
ht->nNextFreeElement = h < LONG_MAX ? h + 1 : LONG_MAX;
}
...
}
I don't think the necessary information is exposed to PHP scripts. Consider:
<?php
$x = array(100 => 'foo');
unset($x[100]);
$x[] = 'bar';
var_dump($x);
?>
array(1) {
[101]=>
string(3) "bar"
}
There would be no way to know that 101 is the next integer given that seemingly empty array, until after adding the item.
If you are building your own array class from scratch, then you could keep track of the next index via a private member variable.
Looks to me like PHP takes the next positive number after the maximum of the index values.
If all else fails, you could simply test against a copy.
// Since PHP passes by copy, we don't even need to explicitly copy.
function get_next_key($copy) {
$copy[] = 'blah';
end($copy);
return key($copy);
}
$key = get_next_key($array);
精彩评论