2014-04-07 4 views
3

아무도 내가 여기서 잘못하고있는 것을 말할 수 있습니까? 배열/해시 유형 및 정렬 쿼리의 모든 가능한 조합에 대해 생각해 볼 수 있고 작동하도록 할 수없는 것처럼 보입니다.해시의 해시 또는 해시 배열의 해시 값으로 Perl 정렬

내가 value1 아래의 해시 심판 분류하는 것을 시도하고있다 : 이런 종류의 루프 사용

my $test = { 
    '1' => { 'value1' => '0.001000', 'value2' => 'red'}, 
    '2' => { 'value1' => '0.005000', 'value2' => 'blue'}, 
    '3' => { 'value1' => '0.002000', 'value2' => 'green'}, 
    '7' => { 'value1' => '0.002243', 'value2' => 'violet'}, 
    '9' => { 'value1' => '0.001005', 'value2' => 'yellow'}, 
    '20' => { 'value1' => '0.0010200', 'value2' => 'purple'} 
}; 

을 :

를 내가 얻을 :

key: 1 value: 0.001000 
key: 3 value: 0.002000 
key: 7 value: 0.002243 
key: 9 value: 0.001005 
key: 2 value: 0.005000 
key: 20 value: 0.0010200 

내가 함께 시도 정수와 같은 일이 일어나는 것 같습니다.

실제로 해시를 반복 할 필요가 없습니다. 나중에 사용하기 위해 주문하기 만하면됩니다. 그 해쉬 배열로하기 쉽지만, 해시 해시로는 안됩니다 ..?

+3

Re. "실제로 해시를 반복 할 필요가 없습니다. 단지 나중에 사용하도록 주문했기 때문입니다." 해시를 정렬 할 수 없습니다. 특정 순서로 키를 반복 할 수 있지만 해시 자체는 정렬되지 않습니다. – ThisSuitIsBlackNot

+0

감사! 그것이 내가 궁극적으로 찾고 있던 대답이었습니다. 위로 배열로 ... 다음 배열을 정렬하는 것이 더 빨리 가정합니다. 해시를 정렬 할 때마다 사용할 때마다 내 현재의 경우 초당 여러 번 사용하는 것이 좋습니다 (새 해시를 만들 수 있다고 생각합니다. 키). – someuser

+0

다시 해시를 정렬 할 수 없습니다. 정렬 된 키 목록을 배열에 저장하고이를 사용하여 해시를 반복하는 데 사용하는 순서를 설정할 수 있지만 해시에서 요소를 추가하거나 제거하지 않는 경우에만 작동합니다. 'my @ sorted = sort keys % hash; for (@sorted) {...}' – ThisSuitIsBlackNot

답변

6

참조에서 키를 호출하지 마십시오. 실제 해시에서 호출합니다.

또한이 $test{$a}->은 이 해시 참조이므로 $test->{$a}이어야합니다.

foreach (sort { $test->{$a}{'value1'} <=> $test->{$b}{'value1'} } keys %{$test}){ 
    print "key: $_ value: $test->{$_}->{'value1'}\n" 
} 

당신은 use strict;이 있고 use warnings; 당신이 문제에 대해 경고하기 위해 다음과 같은 오류가 왔 것, 켜져있는 경우 : 내가 발견 할 수

Global symbol "%test" requires explicit package name 
+0

고마워요. 나는 그것을 시도했지만, 나는 내 % test = (...);로 시도하고 있다고 생각했다. – someuser

+1

및 경고를 사용하면 비교되는 값이 undef – ysth

0

유일한 잘못된 일 해시 심판의 사용입니다 \%{$test} 여기서 해시 %$test을 사용해야합니다. keys 그걸로 작업.

2

간단히 말해서 keys %$test입니다. keys의 인수는 hashref가 아닌 해시 여야합니다. \%${test}$test과 동일합니다.

이 아닌 $test{$a}을 사용하십시오. $test은 해시가 아니고 해시입니다.

foreach (sort { $test->{$a}->{'value1'} <=> $test->{$b}->'{value1'} } keys %$test) { 
    print "key: $_ value: $test->{$_}->{'value1'}\n" 
} 

또는 구문 상 설탕이 짧은 양식 : 첫 번째 화살표 다음에 추가 화살표를 생략 할 수 있습니다. 해시를 처리 할 때 문자열 리터럴 키를 인용 할 필요가 없습니다.

foreach (sort { $test->{$a}{value1} <=> $test->{$b}{value1} } keys %$test) { 
    print "key: $_ value: $test->{$_}{value1}\n" 
} 

는 보통 많은 적어도 디버깅, use warnings; 켤 수 있습니다.

3

다른 답변의 소스와 작동하는 코드 예제를 제공하고 싶습니다. 그들이 말했듯이, 당신은 keys을 인수에 대한 해시 참조와 함께 호출합니다. documentation에 따르면


5.14 펄부터 키 이 저주받은 해시 또는 어레이에 대한 레퍼런스를 포함해야 스칼라 EXPR를 취할 수있다. 인수는 이 자동으로 역 참조됩니다. 이 키 측면은 매우 실험적인 것으로 간주됩니다 ( ).정확한 동작은 향후 Perl 버전에서 변경 될 수 있습니다.

for (keys $hashref) { ... } 
for (keys $obj->get_arrayref) { ... } 

그러나이 않는 나를 위해 일 :

#!/usr/bin/perl 
use strict; 
use warnings; 

my $test = { 
    '1' => { 'value1' => '0.001000', 'value2' => 'red'}, 
    '2' => { 'value1' => '0.005000', 'value2' => 'blue'}, 
    '3' => { 'value1' => '0.002000', 'value2' => 'green'}, 
    '7' => { 'value1' => '0.002243', 'value2' => 'violet'}, 
    '9' => { 'value1' => '0.001005', 'value2' => 'yellow'}, 
    '20' => { 'value1' => '0.0010200', 'value2' => 'purple'} 
}; 


foreach (sort { $test->{$a}->{'value1'} <=> $test->{$b}->{'value1'} } keys \%{$test}) { 
    print "key: $_ value: $test->{$_}->{'value1'}\n" 
} 

예 :이 keys에 입력으로 해시 참조를 사용하여 함께

[email protected]:~/Documents/test/10$ perl test.pl 
key: 1 value: 0.001000 
key: 9 value: 0.001005 
key: 20 value: 0.0010200 
key: 3 value: 0.002000 
key: 7 value: 0.002243 
key: 2 value: 0.005000 
[email protected]:~/Documents/test/10$ perl --version 
This is perl 5, version 14, subversion 2 (v5.14.2) built for x86_64-linux-gnu-thread-multi 
(with 88 registered patches, see perl -V for more detail) 

가 나는 것 권장하지 않습니다.

다른 질문의 조언에 따라 use strictuse warnings을 추가하고 해시 참조를 해시로 변경하는 것이 좋습니다 (%{test}).