2012-07-21 9 views
10

que estoy tratando de entender el código Perl ...número impar de elementos en el anonimato de hash

Si hay una corriente que funciona, si hay 2 o más corrientes se advierte con número impar de elementos en el anonimato picadillo. Parece devolver una matriz en ese caso. ¿Cómo agrego los elementos de la matriz correctamente a @streams? Parece agregar correctamente para el caso HASH en la cláusula if. ¿Es la cláusula else litera?

my $x = $viewedProjectDataObj->{streams}; 

    if (ref($x) eq 'HASH') { 
     push(@streams, $x->{id}); 
    } elsif (ref($x) eq 'ARRAY') { 

     print "$x\n"; 
     print "@$x\n"; 
     my @array = @$x; 
     foreach my $obj (@array) { 
      print "in $obj\n"; 
      print Dumper($obj); 
      push(@streams, ($obj->{id})); 
     } 
    } 

    print "streamcount " . @streams % 2; 
    print Dumper(@streams); 


    my $stream_defect_filter_spec = { 
     'streamIdList' => @streams, 
     'includeDefectInstances' => 'true', 
     'includeHistory' => 'true', 
    }; 

    my @streamDefects = $WS->get_stream_defects($defectProxy, \@cids,    $stream_defect_filter_spec); 
    print Dumper(@streamDefects); 

estoy añadiendo las siguientes líneas ...

if ($defectSummary->{owner} eq "Various") { 
    foreach (@streamDefects) { 
     if (exists($_->{owner})) { 
      $defectSummary->{owner} = $_->{owner}; 
      last; 
     } 
    } 
} 

my $diref = $streamDefects[0]->{defectInstances}; 
if ($diref) { 
    my $defectInstance; 
    if (ref($diref) eq 'HASH') { 
     $defectInstance = $diref; 
    } elsif (ref($diref) eq 'ARRAY') { 
     $defectInstance = @{$diref}[0]; 
    } else { 
     die "Unable to handle $diref (".ref($diref).")"; 
    } 

Ahora errores con API

Web devolvió el código de error S: Servidor: llamar getStreamDefects: No se encontró corriente para el nombre nulo. $ VAR1 = -1; me No se puede utilizar de cadena ("-1") como un ref HASH mientras que los "estrictos árbitros" en uso en la línea 317. xyz-handler.pl

alguna salida Volquete

$VAR1 = { 
     'streamIdList' => [ 
          { 
          'name' => 'asdfasdfadsfasdfa' 
          }, 
          { 
          'name' => 'cpp-62bad47d63cfb25e76b29a4801c61d8d' 

          } 
         ], 
     'includeDefectInstances' => 'true', 
     'includeHistory' => 'true' 
    }; 

Respuesta

14

La lista asignado a un hash es un conjunto de pares clave/valor, por lo que el número de elementos debe ser par.

Debido a que el operador => es poco más que una coma, y ​​la matriz @streams se aplana en la lista, esta

my $stream_defect_filter_spec = { 
    'streamIdList' => @streams, 
    'includeDefectInstances' => 'true', 
    'includeHistory' => 'true', 
}; 

es equivalente a este

my $stream_defect_filter_spec = { 
    'streamIdList' => $streams[0], 
    $streams[1] => $streams[2], 
    $streams[3] => $streams[4], 
    ... 
    'includeDefectInstances' => 'true', 
    'includeHistory' => 'true', 
}; 

así que espero que se puede ver que recibirá la advertencia si tiene incluso número de elementos en la matriz.

para arreglar las cosas que necesita el valor del elemento hash para ser una referencia de matriz , que es un escalar y no alterar el orden de las cosas

my $stream_defect_filter_spec = { 
    'streamIdList' => \@streams, 
    'includeDefectInstances' => 'true', 
    'includeHistory' => 'true', 
}; 

esa manera se puede acceder a la matriz elementos como

$stream_defect_filter_spec->{streamIdList}[0] 

etc.

Y por el camino se puede poner en orden su código substancialmente dejando map hacer lo que es bueno en:

if (ref $x eq 'HASH') { 
    push @streams, $x->{id}; 
} 
elsif (ref $x eq 'ARRAY') { 
    push @streams, map $_->{id}, @$x; 
} 
6

La asignación en:

my $stream_defect_filter_spec = { 
     'streamIdList' => @streams, # <---- THIS ONE 
     'includeDefectInstances' => 'true', 
     'includeHistory' => 'true', 
}; 

no es correcto, se obtiene claves hash de la quinta 1 3 ... conjunto de elementos.

Es posible que desee asignar una referencia a la matriz, no el propio array:

'streamIdList' => \@streams, 

ejemplo para los no deseados (como en su código):

use strict; 
use warnings; 
use Data::Dump; 

my @z = qw(a b c x y z); 
dd \@z; 

my $q = { 
    'aa' => @z, 
}; 
dd $q; 

consecuencia no deseada:

["a", "b", "c", "x", "y", "z"] 
Odd number of elements in anonymous hash at a line 12. 
{ aa => "a", b => "c", x => "y", z => undef } 

             ^-here 

Ejemplo de asignar una referencia

use strict; 
use warnings; 
use Data::Dump; 

my @z = qw(a b c x y z); 
dd \@z; 

my $q = { 
    'aa' => \@z, 
}; 
dd $q; 

produce:

["a", "b", "c", "x", "y", "z"] 
{ aa => ["a", "b", "c", "x", "y", "z"] } 

La diferencia es claramente visible.

+0

pls review answer again. todavía problema –

+0

@DB, se agregaron ambos ejemplos. – jm666

Cuestiones relacionadas