Ограничение a для каждого цикла в облаке тегов

#php #foreach #limit #tag-cloud

#php #foreach #ограничение #облако тегов

Вопрос:

У меня есть следующее облако тегов.

 $rows = $db->loadObjectList();
foreach ($rows as $row)
{
$strAllTags .= $row->caption . ","; 
}

// Store frequency of words in an array
$freqData = array(); 

// Get individual words and build a frequency table
foreach( explode(",", $strAllTags) as $word )
{
// For each word found in the frequency table, increment its value by one
array_key_exists( trim($word), $freqData ) ? $freqData[ trim($word) ]   : $freqData[ trim($word) ] = 0;
}


function getCloud( $data = array(), $minFontSize = 12, $maxFontSize = 32 )
{
$minimumCount = min( array_values( $data ) );
$maximumCount = max( array_values( $data ) );
$spread       = $maximumCount - $minimumCount;
$cloudHTML    = '';
$cloudTags    = array();

$spread = 55;

foreach( $data as $tag => $count )
{
            if ($count > 4)
            {
    $size = $minFontSize   ( $count - $minimumCount ) 
        * ( $maxFontSize - $minFontSize ) / $spread;
    $cloudTags[] = '[[a style="font-size: ' . floor( $size ) . 'px' 
    . '" class="tag_cloud" href="/home?func=searchamp;searchfield=' . $tag 
    .  '"]]' 
    . htmlspecialchars( stripslashes( $tag ) ) . '[[/a]]';
           }
}

return join( "n", $cloudTags ) . "n";
}   
echo getCloud($freqData);
?>
  

Это работает нормально, мне просто нужно ограничить его 20 лучшими результатами, есть идеи относительно того, как сделать это лучше всего?

Спасибо, дайте мне знать, если вам нужно будет просмотреть остальной код.

Ответ №1:

Возьмите другую переменную счетчика и увеличьте в цикле и проверьте, достигнуто ли значение 20, прервите цикл

или

Используйте array_slice

 $data = array_slice($data, 0, 20);

foreach( $data as $tag => $count )
{
.....
  

Комментарии:

1. @shakti Я думал об этом, но разве это не просто вернет 20 результатов в произвольном порядке? Мне нужно, чтобы 20 тегов были наиболее часто используемыми во всей базе данных caption, я отредактировал исходное сообщение, чтобы показать предыдущую часть кода, которая делает это более понятным.

2. @Sherif: чем вы руководствуетесь most used ? Вы говорите о сортировке массива?

3. @shakti ну, я попробовал ваше решение, и оно показывает только 10 тегов, а не 20, но если я использую ($ data, 0, 40), по какой-то причине я получаю 20. Я просто не уверен, действительно ли это топ-20 наиболее используемых, поскольку, когда пользователи сайта помечают свои изображения тегами, облако тегов должно показывать только 20 тегов, которые встречаются чаще всего, затем распределите эти 20 тегов от 12px до 32px

4. @Sherif: Это так из-за этого if ($count > 4) . Будут показаны значения в массиве, если они больше 4.

5. @shakti Я почти уверен, что существует более 20 слов, которые используются более 4 раз. Иначе зачем бы это работало с ($data, 0, 40)? Еще раз извините, это очень ново.

Ответ №2:

Если ваш массив еще не отсортирован, вы можете использовать arsort() для сортировки его по наибольшим результатам. Затем вы можете использовать array_slice() для создания нового массива, содержащего только первые 20 элементов массива:

 arsort($data);
$data = array_slice($data, 0, 20);
  

arsort означает «ассоциативная обратная сортировка». Это просто означает, что он воздействует на ассоциативные массивы, сохраняя их ключи, и сортирует массив в «обратном» (т. Е. от высокого к низкому) порядке по его значениям.

array_slice просто «нарезает» существующий массив. В этом примере говорится: «возьмите $data массив и верните новый массив, содержащий 20 его значений, начиная с первого.

Чтобы учесть замечание, которое вы сделали в комментариях по поводу того, что теги также должны отображаться в порядке по размеру, когда вы хотите, чтобы они были случайными. Вы можете выполнить это, используя shuffle в массиве после того, как вы захватите 20 лучших записей:

 arsort($data);
$data = array_slice($data, 0, 20);
shuffle($data);
  

Комментарии:

1. Где / как я мог бы добавить это в свой код, извините, что я такой новичок!

2. Лучшим методом было бы объединить ваш метод и метод @Shakti. Сначала отсортируйте его, затем прервите на 20.

3. @Sherif: Я добавил простой пример. Обратите внимание, что я изменил функцию с asort на arsort , потому что я был идиотом, когда писал оригинальный ответ.

4. @JohnP: Это может быть скорее личным предпочтением. На самом деле я не думаю, что между этими двумя подходами есть большая разница в производительности, и я думаю, что использование array_splice может быть немного чище.

5. @AgentConundrum Я попробовал ваш метод с arsort, он действительно работает, однако теперь мое облако тегов отображается в порядке от большего к меньшему, тогда как раньше разные размеры тегов были рандомизированы. Друг предлагает мне рандомизировать его впоследствии, не уверен, как я это сделаю?