Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Perl: Общие вопросы > Перебор хеша в цикле и недостающие элементы


Автор: Suppir 20.4.2011, 16:00
Делаю перебор в хеше:

foreach $x(keys %gar){
    print OUT "$gar{$x}{topic}$gar{$x}{pub}\n"
}


значение $gar{$x}{topic} есть всегда
а значения $gar{$x}{pub} есть в 90% случаев.

Perl выдает:
Use of uninitialized value in concatenation (.) or string at !comparator8.pl line 1496, <KON> line 2644738.


Как сделать перебор правильно, чтобы не выскакивало предупреждений? Кроме $gar{$x}{pub} в хеше еще 10 параметров, которые могут быть, а могут и не быть. Нужно выводить их в том случае, если они есть. 

Автор: ginnie 20.4.2011, 16:05
Я бы написал так:
Код

foreach $x(keys %gar){
    print OUT $gar{$x}{$_} if (exists $gar{$x}{$_}) for (qw(topic pub));
    print OUT "\n";
}

Автор: Jimy 20.4.2011, 16:06
Код

no warnings;
foreach $x(keys %gar){
    print OUT "$gar{$x}{topic}$gar{$x}{pub}\n"
}


Код

foreach $x(keys %gar){
    print OUT $gar{$x}{topic}.(defined $gar{$x}{pub} && $gar{$x}{pub})."\n";
}

Автор: arto 20.4.2011, 16:07
perldoc -f exists

Автор: IceSunrise 20.4.2011, 16:09
Suppir, паребираете элементы вы правильно, предупреждение возникает при выводе не существующего элемента хеша. Добавьте дополнительную проверку.
Код

foreach $x(keys %gar){
  if (exists $gar{$x}{pub})
  {
     print OUT "$gar{$x}{topic}$gar{$x}{pub}\n"
  }
  else
  {
    print OUT "$gar{$x}{topic} - \n"
  }
}

Автор: Suppir 20.4.2011, 16:30
Ребята, я использовал ранее предложенные вами варианты. Но мне нужно выводить, например, в log:

print log "$gar{$x}{topic}$gar{$x}{pub}$gar{$x}{prim}$gar{$x}{raw}\n\n"   (и т.д., всего 10 параметров).

Делать проверку всех параметров нереально - слишком много комбинаций. Нужно сделать огромное количество проверок перед выводом. 

Всегда есть параметр $gar{$x}{topic}, а остальные могут быть, а могут и не быть. Нужно вывести в лог только те параметры, которые есть. Но при этом чтобы не возникало предупреждений.

Интересует, как можно добавить в хеш "пустые" элементы? Чтобы и в лог ничего лишнего не выводилось, и предупреждений не возникало. 

Автор: Pfailed 20.4.2011, 16:36
Сделать no warnings или вовсе не делать use warnings уже предлагали?

Автор: Suppir 20.4.2011, 16:39
Pfailed

предупреждения я использую для отлова других ошибок. Очень полезно. 

Интересует, можно ли добавить в хеш "пустые" элементы (которые НЕ будут выводиться в log и не будут вызывать предупреждения).

Автор: ginnie 20.4.2011, 16:46
Suppir, чем мой вариант не устраивает?

Добавить элементы несложно:

Код

$gar{$x}{$_} //= '' for (qw(topic pub prim raw));

Автор: Pfailed 20.4.2011, 16:48
Цитата(Suppir @ 20.4.2011,  16:39)
Pfailed

предупреждения я использую для отлова других ошибок. Очень полезно. 

Интересует, можно ли добавить в хеш "пустые" элементы (которые НЕ будут выводиться в log и не будут вызывать предупреждения).

Код

use strict;
use warnings;

...

{
    # не выводить предупреждения об uninitialized только в этом блоке
    no warnings 'uninitialized';
    print log "$gar{$x}{topic}$gar{$x}{pub}$gar{$x}{prim}$gar{$x}{raw}\n\n";
}



Автор: Suppir 20.4.2011, 16:53
Спасибо, попробую эти варианты:


$gar{$x}{$_} //= '' for (qw(topic pub prim raw))




 # не выводить предупреждения об uninitialized только в этом блоке
    no warnings 'uninitialized';
    print log "$gar{$x}{topic}$gar{$x}{pub}$gar{$x}{prim}$gar{$x}{raw}\n\n";
}

Автор: Jimy 20.4.2011, 20:30
Код

join('', values %{$gar{$x}})

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)