2014-12-10 5 views
0

У меня есть хэш констант, которые я хочу перебирать в другом файле. Таким образом, у меня есть файл, содержащий глобальные константы:Итерация через глобальные хэш-константы в perl

use base qw (Exporter); 

use constant ERROR_CONFIG => { 
    ERROR_STRING => { 
     errorCode => 1234, 
     default => 'Some default text here', 
    }, 
    ERROR_STRING => { 
     errorCode => 12345, 
     default => 'More text', 
    }, 
}; 

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

Я хочу, чтобы перебрать весь ключевой (ERROR_STRING)

Тогда я хочу, чтобы перебрать его и нажать в ссылку на массив, но Perl не кажется, чтобы увидеть его в качестве хэша. Я попытался следующие, но это не сработало, когда я Вытряхивали результат:

my @array =(); 
$stringsRef = \@array; 

my %config = &ERROR_CONFIG; 

foreach my $key (keys %config) { 
    push @$stringsRef, {name => 'ERROR_MESSAGE_' . $key}; 
} 

Data::Dumper::Dumper($stringsArray); 

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

+2

'использование предупреждений;' может быть полезно. –

+1

Удивительно, если бы мы могли просто всплывать по любому вопросу с меткой 'perl' -« эй, вы использовали строгую, используйте предупреждения? Если нет, сначала сделайте это, а затем отформатируйте свой код. – Sobrique

+0

Я используя предупреждения и строгие. – snakespan

ответ

1

У вас есть ошибки в определении константы. Вы должны пр => вместо =:

use constant ERROR_CONFIG => { 
#     here __^^ 
    ERROR_STRING => { 
     errorCode => 1234, 
     default => 'Some default text here', 
    }, 
    ERROR_STRING => { 
     errorCode => 12345, 
     default => 'More text', 
    }, 
}; 

и вы не можете иметь два раза один и тот же ключ в хэш. Я предполагаю, что вы хотите массив:

use constant ERROR_CONFIG => [ 
    ERROR_STRING => { 
     errorCode => 1234, 
     default => 'Some default text here', 
    }, 
    ERROR_STRING => { 
     errorCode => 12345, 
     default => 'More text', 
    }, 
]; 
+0

Это не делает вас постоянным массивом неконстантных ссылок? – Sobrique

+0

@Sobrique: Да, в значительной степени. Он создает подпрограмму 'ERROR_CONFIG', которая возвращает * анонимный массив *, который имеет указанное содержимое. Это похоже на C 'const struct *'. – Borodin

+0

Ссылаясь на комментарий «того же ключа в том же хэше», это уникальные ключи, в которых у меня около 15 различных сообщений об ошибках, все с уникальными ключами вместо ERROR_STRING. – snakespan

0

Ваш код:

use base qw (Exporter); 
use strict; 
use warnings; 

use constant ERROR_CONFIG = { 
    ERROR_STRING => { 
     errorCode => 1234, 
     default => 'Some default text here', 
    }, 
    ERROR_STRING => { 
     errorCode => 12345, 
     default => 'More text', 
    }, 
}; 

дает мне: Can't modify constant item in scalar assignment at line 14, at EOF.

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

Но что еще более важно - вы пытаетесь дублировать свои хэш-ключи, и это просто никогда не будет работать. У вас не может быть два элемента хэша, называемых «ERROR_STRING».

Как отметил другой вклад - изменение его «=>» работает, но вы все равно получите постоянный массив не-постоянных элементов:

print ERROR_CONFIG->[0],"\n"; 
print Dumper ERROR_CONFIG; 

ERROR_CONFIG->[0] = "wibble"; 

print Dumper ERROR_CONFIG; 

&ERROR_CONFIG не собирается работать. & не вызывает разницы в perl, это сигила для подпрограммы. ERROR_CONFIG не является подразделением, поэтому он не будет работать.

Лично я хотел бы предложить либо:

use base qw (Exporter); 
use strict; 
use warnings; 

our %error_config = (
    1234 => 'Some default text', 
    12345 => 'More text', 
); 

foreach my $key (keys %error_config) { 
    print "$key $error_config{$key}\n"; 
} 

И просто принять ваш хэш не является константой. Или, если вам действительно не нужно меняться, используйте либо Hash::Util, и lock_hash_recurse, либо вместо этого сделайте его «частным» хешем и используйте аксессоры.

{ 
    my %private_hash = (
     1234 => 'Some default text', 
     12345 => 'More text', 
    ); 

    sub get_errors { 
     return %private_hash; 
    } 
} 

my %error_codes = get_errors(); 

print Dumper \%error_codes 

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

+2

Код, который он использует это мой [этот вопрос] (http://stackoverflow.com/questions/27388828). Уединенный '=' должен быть '=>' – Borodin

+0

Да, он прав, в моем ответе была ошибка. Я изменю. – snakespan

+0

Я предполагаю, что теперь вопрос изменился, но до того, как вы можете определить хэш констант так, как я выше, и использовать их в контексте хэша? – snakespan

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