#php #arrays
#php #массивы
Вопрос:
У меня вопрос о правильном и быстром поиске в массиве php.
У меня есть входной массив:
array (size=2)
0 =>
array (size=7)
'Videos' =>
array (size=2)
240 =>
array (size=2)
...
120 =>
array (size=2)
...
'Texts' =>
array (size=0)
empty
'Price' => float 0
'QaAudio' => int 1
'QaVideo' => int 3
'Level' => string 'normal' (length=6)
'PreviewPic' =>
array (size=7)
40 =>
array (size=12)
...
60 =>
array (size=12)
...
140 =>
array (size=12)
...
160 =>
array (size=12)
...
320 =>
array (size=12)
...
640 =>
array (size=12)
...
1024 =>
array (size=12)
...
1 =>
array (size=7)
'Videos' =>
array (size=3)
480 =>
array (size=2)
...
360 =>
array (size=2)
...
120 =>
array (size=2)
...
'Texts' =>
array (size=0)
empty
'Price' => float 0
'QaAudio' => int 1
'QaVideo' => int 3
'Level' => string 'sexy' (length=4)
'PreviewPic' =>
array (size=7)
40 =>
array (size=12)
...
60 =>
array (size=12)
...
140 =>
array (size=12)
...
160 =>
array (size=12)
...
320 =>
array (size=12)
...
640 =>
array (size=12)
...
1024 =>
array (size=12)
...
Мне нужно найти в нем видео, которое имеет максимальное значение в ключе Videos.(он имеет 360 240 120 значений, как вы можете видеть в примере) и имеет ключ уровня, равный «нормальному» или «сексуальному» значению.
Я написал какой-то метод для этого:
public function getPresentationVideo($id)
{
$result = [];
$notHardVideos = [];
$profileVideos = $this->getProfilesVideos($id,0,50);
if ($profileVideos amp;amp; count($profileVideos) > 0) {
foreach ($profileVideos as $video) {
if (in_array($video['Level'],['normal','sexy'])) {
$video['maxVideoQuality'] = max(array_keys($video['Videos']));
$notHardVideos[] = $video;
}
}
$keyForMaxQuality = 0;
if (count($notHardVideos) > 1) {
$maxQuality = 0;
foreach($notHardVideos as $key => $video) {
if($video['maxVideoQuality'] > $maxQuality)
{
$maxQuality = $video['maxVideoQuality'];
$keyForMaxQuality = $key;
}
}
}
if (count($notHardVideos) > 0) {
$result = $notHardVideos[$keyForMaxQuality];
unset($result['maxVideoQuality']);
}
}
return $result;
}
Он делает это хорошо.
Но мне интересно, есть ли более эффективный способ сделать это. У вас есть какие-нибудь идеи?
Заранее спасибо.
Ответ №1:
$result = array_reduce($videos, function ($result, array $video) {
if (!in_array($video['Level'], ['normal', 'sexy'])) {
return $result;
}
if (!$result) {
return $video;
}
if (max(array_keys($video['Videos'])) > max(array_keys($result['Videos']))) {
return $video;
}
return $result;
});
Это вернет подмассив, который имеет «нормальный» или «сексуальный» уровень (кстати, FTW ?!) и Который имеет самый высокий ключ в своем подмассиве «Видео». Он не включает никаких других соображений, как вы, кажется, имеете в своем коде, потому что вы не указали точно, каковы эти соображения. Тем не менее, вы должны понять идею и можете добавить дополнительные проверки, если вам нужно.
См. http://php.net/array_reduce за помощью в работе с этой функцией. Короче говоря, это берет каждый элемент в массиве по очереди и сравнивает его с предыдущим лучшим кандидатом. Т.е. $result
Сначала ничего не будет, но когда вы найдете «обычное» или «сексуальное» видео, оно станет этим видео, и при последующих вызовах видео с более высокими ключами выиграет.