Загадка про PHP

Загадка про PHP. Есть массив, описанный таким вот образом:

array (1, '4' => 1, 'a' => 1, 1);

Вопрос: сможете ли вы, не запуская PHP, сказать какой индекс будет у последнего элемента?

Дополнение: буква «a» в индексе — латинская

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

Baka № 3

Не смог. 42? или любой бред ;-)
Если верить документации:

Syntax «index => values», separated by commas, define index and values. index may be of type string or numeric. When index is omitted, a integer index is automatically generated, starting at 0. If index is an integer, next generated index will be the biggest integer index + 1. Note that when two identical index are defined, the last overwrite the first.

, то индексы:
0, '4' (СТРОКА!!!) 'a'(строка), max(0)+1

Но так как PHP сделан по «приципу наибольшего удивления»
(или «через миллениум (с одной н)»),
оказывается, что '4' — не строка…

Улитка № 7
Про правильный ответ:

Эту версию я рассматривал первой.
Второй была версия что последний элемент будет с индексом 'a'. (Она совпадает с правильным ответом, разница лишь в том, как понять смысл вопроса).
Третью версию я написал после того, как прочел в справке о том, что 'a'+1 = 'b'.

Никак не предполагал что php будет вставлять индексы в середину массива.

А вообще, такие вещи решаются программой test.php :-)
Евгений Степанищев автор № 8
Конечно решаются. Но иногда важно знать, что PHP сделает в каком-то случае, так как не задумываясь можно допустить ошибку.
Улитка № 9
Беда в том, что я всё время задумываюсь. И файл test.php у меня постоянно запущен :-)
Евгений Степанищев автор № 10
Я тоже :) Но вот сегодня пропустил одну вещь, связанную с проверкой индекса массивов, но не связанную с задачами.

Кстати, можешь посмотреть вторую задачу.
Baka № 11
$one = 1;
$b_one = (bool)1;

$ten = 10;
$b_ten = (bool)10; # === TRUE

if ($one == $b_one) {print «1:$one == $b_one\n»;}
if ($one === $b_one) {print «2:$one === $b_one\n»;}

if ($ten == $b_ten) {print «3:$ten == $b_ten\n»;}
if ($ten === $b_ten) {print «4:$ten === $b_ten\n»;}

if ($one == $b_ten) {print «5:$one == $b_ten\n»;}
if ($b_one == $ten) {print «6:$b_one == $ten\n»;} # !!!

print «\n»;
if ($b_one == $b_ten) {print «7:$b_one == $b_ten\n»;}
if ($b_one === $b_ten) {print «8:$b_one === $b_ten\n»;}

if ($b_one == TRUE) {print «9:$b_one == TRUE\n»;}
if ($b_one === TRUE) {print «10:$b_one === TRUE\n»;}

if ($one == TRUE) {print «11:$one == TRUE\n»;}
if ($one === TRUE) {print «12:$one === TRUE\n»;}
Baka № 13
Многие говорили. :-) Я об этом когда-то читал у Котерова (который dklab.ru).
Проблема возникает если, например, в функции сравнивать 10 со значеним параметра, думая, что это число
(а получено TRUE или булевский 1 — то есть «булевскость» в функции не видна), то получается
равенство, что не всегда хорошо.
Можно, конечно, все параметры пропускать через явный (int), но это тоже не очень весело.
detail № 15
Спрашивается только, нахрена так объявлять массивы, и как часто это может понадобиться? Как часто это может понадобиться, если писать комментируемый + понятный другим людям код. Не применять, как говорил Расмус Лердорф, лэйтнайт хэкс. :)
Евгений Степанищев автор № 16
Язык надо знать, тогда и код будет понятен. А определятся он может так, например, если этот код генерируется автоматически.
detail № 17
А определятся он может так, например, если этот код генерируется автоматически.

Лихо, лихо. …А ещё на модуль DOM XML бочку катят!
Евгений Степанищев автор № 18
А причём здесь DOM XML? :) Я часто использую автосгенерированные массивы.
detail № 19
Да просто XML-щиков гнобят, мол «шашечки или ехать, будьте проще». То же самое могу сказать про автосгенерированные массивы. :)
Евгений Степанищев автор № 20
Автосгенерированные массивы — необходимость. Они помогают кешировать данные.
mivlad № 21
А не быстрее ли автосгенерированные массивы хранить в сериализованном виде?
Евгений Степанищев автор № 22
Не быстрее. Unserialize гораздо медленее, чем include.
mivlad № 25
Не быстрее. Unserialize гораздо медленее, чем include.

Точно? Только что проверил — десериализация раза в полтора быстрей полноценного парсинга. Тестовый (генерирующий) скрипт:

for($i=0; 10000>$i; $i++)$a[]=mt_rand()%2?mt_rand():md5(mt_rand());
echo microtime(),"\n";
$fp=fopen('s','w');
fwrite($fp,serialize($a));
fclose($fp);
echo microtime(),"\n";
$fp=fopen('p','w');
fwrite($fp,'? $a='.var_export($a,1).'?'); // около вопросиков добавить угловые скобки
fclose($fp);
echo microtime(),"\n";

Обратный, думаю, сам напишешь :)
Кстати, serialize действительно медленнее, чем var_export.

Евгений Степанищев автор № 26
Сравни unserialize и include. Ты сделал наоборот.
mivlad № 27
Евгений Степанищев,
Сравни unserialize и include. Ты сделал наоборот.

О чём и сказал (согласен, недостаточно внятно). Как раз в этом обратном случае ты прав, но unserialize быстрее, чем include.

Евгений Степанищев автор № 28
mivlad, Действительно — медленее на треть. Массив из 10000 элементов (строк по 32 символа) в цикле из 100 операций выполнился для unserialize за 10 секунд, для include — за 16. Любопытно. Буду использовать serialize там, где читаемость результата не важна.
detail № 23
Автосгенерированные массивы — необходимость. Они помогают кешировать данные.
Я не знаю твоей позиции по XML, поэтому не буду продолжать. :)