Reputation: 1496
I have an array that looks like the following and I receive it from an API and therefore, can't change it:
[
[
'id' => '123',
'title' => 'Test',
'categories' => [
[
'id' => 1
]
]
],
[
'id' => '456',
'title' => 'Test',
'categories' => [
[
'id' => 2
]
]
]
]
I want to only get the complete array which contains 'categories' => [ 'id' => 1 ]
I've tried something like this:
$filteredArray = array_filter($array, function ($value) {
return ($value['categories'] === 1);
});
This results in an empty array. How do I achieve this?
Upvotes: 1
Views: 233
Reputation: 48000
Although the sample data only contains one entry with an id
element per subset, I'll assume multiple subarray rows are possible.
Code: (Demo)
var_export(
array_filter(
$array,
fn($row) => array_column($row['categories'], 'id', 'id')[1] ?? null
)
);
As a slight microoptimization, using a conditionally breakable loop inside the callback can be used at the expense of more verbose code. (Demo)
var_export(
array_filter(
$array,
function($row) {
foreach ($row['categories'] as ['id' => $id]) {
if ($id !== 1) {
return false;
}
}
return true;
}
)
);
Upvotes: 0
Reputation: 3005
This would do it. You need to make sure you go all the way to the deepest level for filtering.
Not the cleanest solution ( there are probably nicer ones ), but it works:
Here is the sandbox for testing
$array = [
[
'id' => '123',
'title' => 'Test',
'categories' => [
[
'id' => 1
]
]
],
[
'id' => '456',
'title' => 'Test',
'categories' => [
[
'id' => 2
]
]
]
];
$filteredArray = array_filter($array, function ($value) {
return array_filter($value['categories'], function($categories) {
return $categories['id'] === 1;
});
});
// Or the shorter version
$filteredArray = array_filter(
$array,
fn($value) => array_filter(
$value['categories'],
fn($categories) => $categories['id'] === 1
)
);
print_r($filteredArray);
Upvotes: 2
Reputation: 1496
I have fixed the issue. The types were wrong. The category id in the array is of type int, and I was comparing it with a string value using ===
. Casting either one of them to the type of the other has fixed the issue.
Upvotes: 0