Fai W
Fai W

Reputation: 115

Filter with callback misses some condition

I have the following code to filter an array in PHP; it works fine. But after adding more filtering conditions, it stopped working.

Working code

$s_item = array_values(array_filter($itmlist, function ($itmlist) {
    return ($itmlist['itmslsprc'] > 0);
    }
)); 

Code that doesn't work after adding more conditions

$s_item = array_values(array_filter($itmlist, function ($itmlist) {
    return ($itmlist['itmslsprc'] > 0 && $today >= $itmlist['itmslsfr']  &&  $today <= $itmlist['itmslsto']);
    }
));

Both $today and the other dates have been initialised in format 2021-01-12 00:00:00.

Can anyone tell what might have gone wrong? Thanks in advance for any advice.

Upvotes: 1

Views: 309

Answers (3)

Kamafeather
Kamafeather

Reputation: 9845

As mentioned, you can just import the variable in the the callback's scope, relying on use statement.

PHP Closures don't bind automatically to the outer scope (like it happens in languages like Javascript).

But if you stick to a more functional programming paradigm (and work with PHP >=7.4), you can avoid the manual import and rely on PHP Arrow Functions.

$today = // your value here

$s_item = array_values(array_filter($itmlist, fn($itmlist) =>
    $itmlist['itmslsprc'] > 0 &&
    $today >= $itmlist['itmslsfr'] &&
    $today <= $itmlist['itmslsto']
));

fn() => returnExpression will have access to $today.

Note

This is a copy-by-value, as reported in the manual:

When a variable used in the expression is defined in the parent scope it will be implicitly captured by-value.

In case you want to modify the outer variable, and want no additional closure parameters, then use statement is your best option.

Upvotes: 0

devtestcrowd
devtestcrowd

Reputation: 44

if your today is outside the function you can use "use"

Upvotes: 0

Hammad Ahmed khan
Hammad Ahmed khan

Reputation: 1671

if your today is outside the function you can use it inside the function like this :

$s_item = array_values(array_filter($itmlist, function ($itmlist) use($today) {
    return ($itmlist['itmslsprc'] > 0 && $today >= $itmlist['itmslsfr']  &&  $today <= $itmlist['itmslsto']);
    }
));

Upvotes: 4

Related Questions