Reputation: 12526
I want to avoid scanning the array twice. Something like TryGetValue in C#.
Upvotes: 3
Views: 3259
Reputation: 21321
UPDATE
This is not recommended practice. Because @
suppresses all exceptions in that expression.
However, AFAIK, it is the only efficient way to meet OP's stated criteria (see comment on question):
I want to avoid errors/warnings and I want to avoid scanning the array twice.
Recommended practice can be seen in Amit's answer.
That is, don't "micro-optimize" your code. Don't be so concerned about "scanning the array twice". Write clean, robust code. Later, if testing finds a performance problem, evaluate then how to improve performance.
Do handle errors and unexpected conditions (exceptions).
ORIGINAL ANSWER
@jszobody gave an answer in a comment on the question. Expanding on his comment:
What do you want to return, if the array key doesn't exist?
If null
, then one approach is "just do it":
@$array[$key]
("@" suppresses warning.)
If something else, and you don't store null values in array - so you don't ever want null
to be returned - then this code becomes:
@$array[$key] ?? $YourDefaultValue
Unless your design BOTH 1) allows storing of null
values in the array, AND 2) wants a default other than null
. If both of these conditions are true, then you would need to explicitly test whether the key exists, using array_key_exists
.
Upvotes: -1
Reputation: 3792
Check these microbenchmarks I created on 3v4l.
Here are the functions.
function tryGetValue1( $array, $key, Closure $default ) {
return array_key_exists($key, $array)
? $array[$key] : $default();
}
function tryGetValue2( $array, $key, Closure $default ) {
return ($value = @$array[$key]) !== null || array_key_exists($key, $array)
? $value : $default();
}
function tryGetValue3( $array, $key, Closure $default ) {
return isset($array[$key]) || array_key_exists($key, $array)
? $array[$key] : $default();
}
function tryGetValueNotNull1( $array, $key, Closure $default ) {
return ($value = @$array[$key]) !== null
? $value : $default();
}
function tryGetValueNotNull2( $array, $key, Closure $default ) {
return isset($array[$key])
? $array[$key] : $default();
}
It depends on if you care about null, and what version of PHP you're using.
Looks like the compilers try to optimize toward the isset and array_key_exists operations, at least for small arrays. This might imply that arrays have their own internal iterator state for this and similar purposes.
Interestingly, you can combine isset and array_key_exists (see tryGetValue3) and come out ahead sometimes.
This isn't a fully appropriate benchmark, as there are no null existing keys defined in the test array. Feel free to expand on the example. :)
Upvotes: -1
Reputation: 76636
No, there isn't a built-in function that does what you want. However, it's not hard to write a new one:
function tryGetValue($array, $key) {
return (array_key_exists($key, $array)) ? $array[$key] : NULL;
}
Example usage:
$array = array('foo' => 'bar', 'baz', 'bak', 'bam');
var_dump(tryGetValue($array, 'foo')); // string(3) "bar"
var_dump(tryGetValue($array, 's')); // NULL
var_dump(tryGetValue($array, 2)); // string(3) "bam"
var_dump(tryGetValue($array, 4)); // NULL
Upvotes: 2