2011-03-21 24 views
16

Esta sintaxis funciona:Perl: Asignación de una matriz a un hash

$b{"x"} = [1,2,3]; 
pp %b; 
# Displays ("x", [1, 2, 3]) 

Pero tengo que ser capaz de crear de forma dinámica el contenido de la matriz y asignarle más tarde. Esto no funciona; ayuda, ¿cuál es la parte obvia que me falta?

@a = [1,2,3]; 
$b{"x"} = @a; 
pp %b; 
# Shows up as ("x", 1) ... not what I want or expected. 

Probé estas variaciones, también.

$b{"x"} = [@a]; # ("x", [[1, 2, 3]]) ...close 

$b{"x"} = \@a; # ("x", [[1, 2, 3]]) 

$b{"x"} = [\@a]; # ("x", [[[1, 2, 3]]]) 

$b{"x"} = %a; # ("x", 0) 

$b{"x"} = $a; # ("x", undef) 

$b{"x"} = [$a]; # ("x", [undef]) 

$b{"x"} = @{@a}; # ("x", 0) 

Y, a ser posible, me gustaría ser capaz de obtener la matriz de vuelta más tarde como una matriz.

+0

Mi "impresión bonita "la función provino de CPAN - use Data :: Dump qq/pp /; –

Respuesta

29

La parte que falta es que @a = [1,2,3] no hace una matriz con 3 elementos. Hace una matriz con un elemento que es un arrayref.

Querías decir @a = (1,2,3).

Para asignar esa matriz a un elemento hash, usaría $b{"x"} = [@a] o $b{"x"} = \@a, dependiendo de lo que intente hacer. [@a] hace una nueva matriz que contiene una copia del contenido actual de @a. Si el contenido de @a cambia después de eso, no tiene efecto en $b{x}.

Por otro lado, \@a le da una referencia a @a sí mismo. Si luego cambia los contenidos de @a, eso será visible en $b{x} (y viceversa).

+0

Gracias, he estado mirando los corchetes y viendo paréntesis. –

12

Debe leer la documentación perlref que habla de referencias.

hay una diferencia en cómo se almacenan las matrices:

# this is an array in an array variable 
@a = (1, 2, 3); 

versos almacenar una referenciaa una matriz:

# this is an array in a scalar variable stored as a reference to the previous array: 
$b = \@a; 

funcional que funciona como un puntero. Por lo tanto, también puede almacenar esta referencia en un hash:

$x{'something'} = \@a; 

Todo funciona bien. Lo que no se ha dado cuenta es que [] s crea referencias en una matriz, que no puede almacenar en una variable de matriz. Debe almacenarlo en un escalar. Así, este lugar:

$c = [1, 2, 3]; 
$x{'else'} = $c; 

va a funcionar.

Y acceder y modificar la matriz antes de hacer la segunda asignación se puede hacer usando:

$c->[3] = '4'; 

o usándolo en forma array derreferenciándolo primera

push @$c, 5; 
Cuestiones relacionadas