2009-11-18 6 views
3

Может кто-нибудь помочь мне понять вывод этой программы на Perl:Почему автовивитация Perl работает в этом случае?

use Data::Dumper; 
my %hash; 
$hash{hello} = "foo"; 
$hash{hello}{world} = "bar"; 
print $hash{hello} . "\n"; 
print $hash{hello}{world} . "\n"; 
print Dumper(\%hash); 

И вывод:

foo 
bar 
$VAR1 = { 
      'hello' => 'foo' 
     }; 

Где "Foo" приходит? Почему он не распечатывается с помощью самосвала?

Обратите внимание, что если я поменять порядок назначений:

use Data::Dumper; 
my %hash; 
$hash{hello}{world} = "bar"; 
$hash{hello} = "foo"; 
print $hash{hello} . "\n"; 
print $hash{hello}{world} . "\n"; 
print Dumper(\%hash); 

мой вывод, что я ожидаю:

foo 

$VAR1 = { 
      'hello' => 'foo' 
     }; 

EDIT: Я знаю, что use strict; бы поймать, но я Мне больше интересно знать как строка «foo» все еще печатается.

+0

Добавление 'use strict' должно помочь раскрыть это –

+0

Когда вы говорите * Где находится« foo »? *, Вы имеете в виду ** bar **? –

+0

Нет, я ожидал, что там будет только бар, но теперь я вижу, что происходит из-за вашего приятного ответа (и комментария Криса) ниже. – tster

ответ

17

Ваш код отсутствует

use strict; 
 
C:\Temp> hui 
Can't use string ("foo") as a HASH ref while "strict refs" in use at 
C:\Temp\hui.pl line 7. 

Убедитесь, что все скрипты начинаются с:

use strict; 
use warnings; 

Дано:

$hash{hello} = "foo"; 

$hash{hello} является НЕ хеш-ссылка.

$hash{hello}{world} = "bar"; 

трактует строковые "foo" в качестве эталона хэш и создает хэш %main::foo и устанавливает $foo{world} в "bar".

Когда вы делаете:

print Dumper \%hash; 

он печатает только содержимое %hash. Принимая во внимание, что, когда вы делаете

print $hash{hello}{world} . "\n"; 

это печатает $foo{world}.

Без strict вы не узнаете, что скрипт попирает все пространство имен пакетов.

Добавить

print Dumper \%main::; 

или

print Dumper \%main::foo; 

проверять таблицу символов после запуска этого.

+2

Добавление использования строгих находит проблемы с этим, но это не говорит мне, как я получаю вывод, который я есть. Это больше зависит от внутреннего вопроса Perl, чем «plz fix my codez». – tster

+3

. Что происходит, это автоматическое преобразование переменной, называемой '% foo' (потому что это то, что происходит, когда вы используете строку в качестве ссылки). Добавьте 'print Dumper (\% foo)' в конец вашего кода, чтобы увидеть опасные результаты. –

+0

Крис, это здорово, спасибо! – tster

1

Если вы используете строгую, вы получите сообщение об ошибке со своим скриптом.

Нельзя использовать строку ("foo") как HASH ref при использовании "строгих ссылок" ...

2

В основном строка «Foo» является единственным значением %hash, но (из-за отсутствия strictyness)% Foo создается, что содержит (world => "bar")

1

Autovivification работает только тогда, когда вы начинаете с неопределенными значениями. Поскольку ваш $hash{hello} не является неопределенным значением, вы не можете автогенерировать следующий уровень. Вместо этого вы в конечном итоге используете $hash{hello} в качестве мягкой ссылки.

Смежные вопросы