Foreach php last value

Как определить первую и последнюю итерацию в цикле foreach?

Вопрос прост. У меня есть цикл foreach в моем коде:

В этом цикле я хочу реагировать по-разному, когда мы находимся на первой или последней итерации.

Вы можете использовать счетчик:

$i = 0; $len = count($array); foreach ($array as $item) < if ($i == 0) < // first >else if ($i == $len - 1) < // last >// … $i++; > 

Если ваш массив имеет уникальные значения массива, то определение первого и последнего элемента тривиально:

Это работает, если последние и первые элементы появляются только один раз в массиве, иначе вы получите ложные срабатывания. Поэтому вам нужно сравнить ключи (они уникальны).

foreach($array as $key => $element)

Обновление: некоторые люди обеспокоены производительностью и / или изменением указателя массива внутри цикла foreach. Для них вы можете кэшировать значение ключа перед циклом.

reset($array); $first = key($array); foreach($array as $key => $element)

Чтобы найти последний элемент, я считаю, что этот кусок кода работает каждый раз:

Более упрощенная версия вышеизложенного и предполагающая, что вы не используете пользовательские индексы …

$len = count($array); foreach ($array as $index => $item) < if ($index == 0) < // first >else if ($index == $len - 1) < // last >> 

Версия 2 – Потому что я пришел к ненависти, используя другое, если это не необходимо.

$len = count($array); foreach ($array as $index => $item) < if ($index == 0) < // first // do something continue; >if ($index == $len - 1) < // last // do something continue; >> 

Вы можете удалить первый и последний элементы из массива и обработать их отдельно.
Как это:

Удаление всего форматирования в CSS вместо встроенных тегов улучшит ваш код и ускорит время загрузки.

Вы также можете избежать смешивания HTML с php-логикой, когда это возможно.
Ваша страница может быть сделана гораздо более читаемой и поддерживаемой, разделяя такие вещи:

 function show_subcat($val) < ?> 
function show_cat($item) < ?>
$item['xcatid'])) ; foreach($subcat as $val) show_subcat($val); ?>
function show_collection($c) < ?>
$c['xcollectionid'])); foreach($cat as $item) show_cat($item); ?>
?>
$first = true; foreach ( $obj as $value ) < if ( $first ) < // do something $first = false; //in order not to get into the if statement for the next loops >else < // do something else for all loops except the first >> 
//Store the last key $lastkey = key(end($array)); foreach($array as $key => $element)

1: Почему бы не использовать простой for утверждения? Предполагая, что вы используете реальный массив, а не Iterator вы можете легко проверить, равна ли переменная счетчика 0 или меньше, чем целое число элементов. По-моему, это самое чистое и понятное решение …

$array = array( . ); $count = count( $array ); for ( $i = 0; $i < $count; $i++ ) < $current = $array[ $i ]; if ( $i == 0 ) < // process first element >if ( $i == $count - 1 ) < // process last element >> 

2: Вы должны использовать Nested Sets для хранения вашей древовидной структуры. Кроме того, вы можете улучшить все это, используя рекурсивные функции.

$arr = array(1, 2, 3, 4, 5, 6, 7, 8, 9, 10); foreach ($arr as $a) < // This is the line that does the checking if (!each($arr)) echo "End!\n"; echo $a."\n"; > 

Для сценариев генерации SQL-запросов или всего, что делает другое действие для первого или последнего элемента, оно намного быстрее (почти в два раза быстрее), чтобы избежать использования проверок ненужных переменных.

Текущее принятое решение использует цикл и проверку внутри цикла, которые будут сделаны every_single_iteration, правильный (быстрый) способ сделать это следующий:

$numItems = count($arr); $i=0; $firstitem=$arr[0]; $i++; while($i <$numItems-1)< $some_item=$arr[$i]; $i++; >$last_item=$arr[$i]; $i++; в $numItems = count($arr); $i=0; $firstitem=$arr[0]; $i++; while($i <$numItems-1)< $some_item=$arr[$i]; $i++; >$last_item=$arr[$i]; $i++; 

Небольшой домашний тест показал следующее:

test1: 100000 прогонов модели морга

время: 1869.3430423737 миллисекунды

test2: 100000 пробегов модели, если последняя

время: 3235.6359958649 миллисекунд

И вполне понятно, что проверка стоит много, и, конечно же, становится еще хуже, чем больше проверяет переменные;)

Использование логической переменной по-прежнему является самым надежным, даже если вы хотите проверить первое появление значения $value (я нашел его более полезным в моей ситуации и во многих ситуациях) , например:

$is_first = true; foreach( $array as $value ) < switch ( $value ) < case 'match': echo 'appeared'; if ( $is_first ) < echo 'first appearance'; $is_first = false; >break; > > if( !next( $array ) ) < echo 'last value'; >> 

Затем как насчет !next( $array ) чтобы найти последнее $value которое вернет true если нет next() значения для итерации.

И я предпочитаю использовать цикл for вместо foreach если я собираюсь использовать счетчик, например:

$len = count( $array ); for ( $i = 0; $i < $len; $i++ ) < $value = $array[$i]; if ($i === 0) < // first >elseif ( $i === $len - 1 ) < // last >// … $i++; > 

С ключами и значениями это работает также:

foreach ($array as $key => $value) < if ($value === end($array)) < echo "LAST ELEMENT!"; >> 

Самый эффективный ответ от @morg, в отличие от foreach , работает только для правильных массивов, а не для объектов хеш-карт. Этот ответ позволяет избежать накладных расходов условного оператора для каждой итерации цикла, как и в большинстве из этих ответов (включая принятый ответ), специально обрабатывая первый и последний элемент и перебирая средние элементы.

Функция array_keys может использоваться для эффективной работы ответа, например foreach :

$keys = array_keys($arr); $numItems = count($keys); $i=0; $firstItem=$arr[$keys[0]]; # Special handling of the first item goes here $i++; while($i <$numItems-1)< $item=$arr[$keys[$i]]; # Handling of regular items $i++; >$lastItem=$arr[$keys[$i]]; # Special handling of the last item goes here $i++; в $keys = array_keys($arr); $numItems = count($keys); $i=0; $firstItem=$arr[$keys[0]]; # Special handling of the first item goes here $i++; while($i <$numItems-1)< $item=$arr[$keys[$i]]; # Handling of regular items $i++; >$lastItem=$arr[$keys[$i]]; # Special handling of the last item goes here $i++; 

Я не проводил бенчмаркинг по этому вопросу, но логика не была добавлена ​​в цикл, который был самым большим ударом по производительности, поэтому я подозреваю, что эталонные тесты с эффективным ответом довольно близки.

Если бы вы хотели функционировать такого рода вещи, я сделал поворот в такой функции iterateList . Хотя, возможно, вы захотите провести сравнение кода gist, если вы серьезно обеспокоены эффективностью. Я не уверен, сколько накладных расходов вызывает все функции invocation.

Я столкнулся с этим вопросом, когда у меня такая же проблема. Мне нужно только получить первый элемент, тогда я переанализирую свой код, пока это не придет мне в голову.

$firstElement = true; foreach ($reportData->result() as $row) < if($firstElement) < echo "first element"; $firstElement=false; >// Other lines of codes here > 

Вышеприведенные коды являются большими и полными, но если вам нужен только первый элемент, вы можете попробовать этот код.

Не уверен, что это все еще необходимо. Но следующее решение должно работать с итераторами и не требует count .

); foreach_first_last(array('aa'), function ($key, $value, $step, $first, $last) < echo intval($first), ' ', intval($last), ' ', $step, ' ', $value, PHP_EOL; >); echo PHP_EOL; foreach_first_last(array('aa', 'bb', 'cc'), function ($key, $value, $step, $first, $last) < echo intval($first), ' ', intval($last), ' ', $step, ' ', $value, PHP_EOL; >); echo PHP_EOL; function foreach_first_last($array, $cb) < $next = false; $current = false; reset($array); for ($step = 0; true; ++$step) < $current = $next; $next = each($array); $last = ($next === false || $next === null); if ($step >0) < $first = $step == 1; list ($key, $value) = $current; if (call_user_func($cb, $key, $value, $step, $first, $last) === false) < break; >> if ($last) < break; >> > 

Вы также можете использовать анонимную функцию:

$indexOfLastElement = count($array) - 1; array_walk($array, function($element, $index) use ($indexOfLastElement) < // do something if (0 === $index) < // first element's treatment >if ($indexOfLastElement === $index) < // last not least >>); 

Следует упомянуть еще три вещи:

  • Если ваш массив не индексируется строго (численно), вы должны сначала array_values свой массив через array_values .
  • Если вам нужно изменить $element вы должны передать его по ссылке ( &$element ).
  • Любые переменные извне анонимной функции, которые вам нужны внутри, вам нужно будет перечислить их рядом с $indexOfLastElement внутри use конструкции, опять же по ссылке, если необходимо.

Источник

Foreach php last value

The foreach construct provides an easy way to iterate over arrays. foreach works only on arrays and objects, and will issue an error when you try to use it on a variable with a different data type or an uninitialized variable. There are two syntaxes:

foreach (iterable_expression as $value) statement foreach (iterable_expression as $key => $value) statement

The first form traverses the iterable given by iterable_expression . On each iteration, the value of the current element is assigned to $value .

The second form will additionally assign the current element’s key to the $key variable on each iteration.

Note that foreach does not modify the internal array pointer, which is used by functions such as current() and key() .

In order to be able to directly modify array elements within the loop precede $value with &. In that case the value will be assigned by reference.

$arr = array( 1 , 2 , 3 , 4 );
foreach ( $arr as & $value ) $value = $value * 2 ;
>
// $arr is now array(2, 4, 6, 8)
unset( $value ); // break the reference with the last element
?>

Reference of a $value and the last array element remain even after the foreach loop. It is recommended to destroy it by unset() . Otherwise you will experience the following behavior:

// without an unset($value), $value is still a reference to the last item: $arr[3]

foreach ( $arr as $key => $value ) // $arr[3] will be updated with each value from $arr.
echo » < $key >=> < $value >» ;
print_r ( $arr );
>
// . until ultimately the second-to-last value is copied onto the last value

// output:
// 0 => 2 Array ( [0] => 2, [1] => 4, [2] => 6, [3] => 2 )
// 1 => 4 Array ( [0] => 2, [1] => 4, [2] => 6, [3] => 4 )
// 2 => 6 Array ( [0] => 2, [1] => 4, [2] => 6, [3] => 6 )
// 3 => 6 Array ( [0] => 2, [1] => 4, [2] => 6, [3] => 6 )
?>

It is possible to iterate a constant array’s value by reference:

Note:

foreach does not support the ability to suppress error messages using @ .

Some more examples to demonstrate usage:

/* foreach example 1: value only */

foreach ( $a as $v ) echo «Current value of \$a: $v .\n» ;
>

/* foreach example 2: value (with its manual access notation printed for illustration) */

$i = 0 ; /* for illustrative purposes only */

foreach ( $a as $v ) echo «\$a[ $i ] => $v .\n» ;
$i ++;
>

/* foreach example 3: key and value */

$a = array(
«one» => 1 ,
«two» => 2 ,
«three» => 3 ,
«seventeen» => 17
);

foreach ( $a as $k => $v ) echo «\$a[ $k ] => $v .\n» ;
>

/* foreach example 4: multi-dimensional arrays */
$a = array();
$a [ 0 ][ 0 ] = «a» ;
$a [ 0 ][ 1 ] = «b» ;
$a [ 1 ][ 0 ] = «y» ;
$a [ 1 ][ 1 ] = «z» ;

foreach ( $a as $v1 ) foreach ( $v1 as $v2 ) echo » $v2 \n» ;
>
>

/* foreach example 5: dynamic arrays */

foreach (array( 1 , 2 , 3 , 4 , 5 ) as $v ) echo » $v \n» ;
>
?>

Unpacking nested arrays with list()

It is possible to iterate over an array of arrays and unpack the nested array into loop variables by providing a list() as the value.

foreach ( $array as list( $a , $b )) // $a contains the first element of the nested array,
// and $b contains the second element.
echo «A: $a ; B: $b \n» ;
>
?>

The above example will output:

You can provide fewer elements in the list() than there are in the nested array, in which case the leftover array values will be ignored:

foreach ( $array as list( $a )) // Note that there is no $b here.
echo » $a \n» ;
>
?>

The above example will output:

A notice will be generated if there aren’t enough array elements to fill the list() :

foreach ( $array as list( $a , $b , $c )) echo «A: $a ; B: $b ; C: $c \n» ;
>
?>

The above example will output:

Notice: Undefined offset: 2 in example.php on line 7 A: 1; B: 2; C: Notice: Undefined offset: 2 in example.php on line 7 A: 3; B: 4; C:

Источник

Читайте также:  Шаблон панели администратора html
Оцените статью