2015-08-11 2 views
0

Как я могу вернуть хеш или массив из подпрограммы, в зависимости от того, чего хочет пользователь?Необязательно возвращать массив или хэш из подпрограммы?

В принципе, я хочу подпрограмму, когда при запросе вернуть хэш она вернет хэш, но когда его попросят вернуть массив, он вернет массив, содержащий ключи от этого хэша.

например:

my %hash = foo(); 

my @array = foo(); # @array contains "keys %hash" 

# pseudo code 
sub foo { 

    # Define a hash 
    my %hash = (
     'key1' => 'val1', 
     'key2' => 'val2', 
     'key3' => 'val3', 
    ); 

    # I know this is not valid Perl code, but it represents what I want. 
    return keys %hash if wantarray; 
    return %hash  if wanthash; 
} 

Я знаю, что вы можете использовать wantarray, чтобы определить, хотите ли вы массив или скаляр должен быть возвращен, но мне нужно схожую функциональность для необязательно возвращая массив или хэш.

+2

В Perl нет такой вещи, как «массив контекста», я думаю: это либо _list_, либо скалярный, либо пустой контекст. Зачем вам такая функциональность? – raina77ow

+1

Возможно, модуль [Want] (http://search.cpan.org/~robin/Want-0.26/Want.pm) будет интересен для вас. – raina77ow

+1

всегда возвращает \% хеш и позволяет вызывающему пользователю 'my @array = keys% {foo()}' или 'my% hash =% {foo()}' (или еще лучше, просто 'my $ hasherf = foo() ') – ysth

ответ

2

Ваша подпрограмма может возвращать массив или reference to hash.

my @array = foo(); # @array contains "keys %hash" 
my $hash_reference = foo(); 

print $array[0],"\n"; # keys returned by foo are in random order 
print $hash_reference->{key1},"\n"; 


# sample code 
sub foo { 

    # Define a hash 
    my %hash = (
     'key1' => 'val1', 
     'key2' => 'val2', 
     'key3' => 'val3', 
    ); 

    if(wantarray) { 
     return keys %hash; 
    }else{ 
     return \%hash 
    } 
} 
1

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

sub foo { 
    my $want_keys = shift; 

    my %hash = (a => 1, b => 2, c => 3,); 

    return keys %hash if $want_keys; 

    return %hash; 
} 

my %hash = foo(); 

my @keys = foo(1); # or foo('keys'); 

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

sub foo { 
    my %hash = (a=>1, b=>2); 
    return %hash if wantarray; 
    return [keys %hash]; 
} 

my $keys = foo(); 
my %hash = foo(); 
+0

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

+0

Я обновил свой ответ единственным способом, который я могу придумать, чтобы сделать это (верните хеш, если 'wantarray', в противном случае верните isf с ключами) – stevieb

+0

Смешно, это полная противоположность ответа Анджей :) Оба кажется, лучшие варианты. Я выбрал его, так как с помощью функции wantarray для возврата массив логичнее имеет смысл, чем возвращать хэш, но я дал вашему ответу +1, потому что он также не менее важен. – tjwrona1992

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