2013-05-28 29 views
6

Właśnie spojrzał z niedowierzaniem na tej sekwencji:Lista argumentów podprogramu perl - "przekazać przez alias"?

my $line; 
$rc = getline($line); # read next line and store in $line 

I zrozumiał cały czas, że argumenty Perl były przekazywane przez wartość, więc kiedy mam potrzebne do przekazania w dużej strukturze, albo przekazać w zmiennej być zaktualizowany, zdałem ref.

Czytając drobnym drukiem w perldoc, dowiedziałem się, że @_ składa się z aliasów do zmiennych wymienionych na liście argumentów. Po przeczytaniu następnego fragmentu danych, getline() zwraca je z $ _ [0] = $ dane;, który przechowuje $ dane bezpośrednio w $ linia.

Ja podoba mi się to - to jak przekazywanie przez odniesienie w C++. Jednak nie znalazłem sposobu na przypisanie bardziej znaczącej nazwy do $ _ [0]. Czy jest jakiś?

+0

Tak, Perl jest zawsze przekazywany przez odniesienie – newacct

+0

Cóż - nie mylić z referencjami Perla, które są bardziej jak wskaźniki C, ponieważ muszą być jawnie dereferencyjne. – Chap

+0

Nie byłby $ arg = shift; $ arg = $ data; zrób to? Czy zamiast tego "przesunięcie" spowoduje utworzenie kopii argumentu? EDYCJA: Przetestowałem adresy przekazanego skalaru i argument "shift", a wyniki mówią, że shift robi kopię, więc przypisanie do $ arg jak wyżej nie wpłynie na linię $ zgodnie z przeznaczeniem. :( – sundar

Odpowiedz

7

Można, jego niezbyt ładna:

use strict; 
use warnings; 

sub inc { 
    # manipulate the local symbol table 
    # to refer to the alias by $name 
    our $name; local *name = \$_[0]; 

    # $name is an alias to first argument 
    $name++; 
} 

my $x = 1; 
inc($x); 
print $x; # 2 
+1

Znaczne upięknienie jest dostępne z 'Dane :: Alias'. – darch

+0

również, Metoda: :: Podpisy ma [cecha aliasu] (https://metacpan.org/module/Method:: Znaków #Parameter-traits) –

0

Najłatwiej jest prawdopodobnie tylko do korzystania z pętli, ponieważ pętli alias ich argumentów do nazwy; tj

sub my_sub { 
    for my $arg ($_[0]) { 
    code here sees $arg as an alias for $_[0] 
    } 
} 
+0

Prawdziwe, ale nie do końca to, czego szukałem - byłoby miło, gdybyśmy chcieli nadać różne nazwy poszczególnym argumentom. Wygląda na to, że Joel to robi, ale jak sam mówi, jest to dość nieładne – Chap

+0

@Chap: Dodałem odpowiedź http://stackoverflow.com/a/17343595/8127, który pozwala na różne nazwy dla każdego arg, ale to też jest niechlujny na swój sposób. – sundar

0

Wersja @ kodu Steve'a, który pozwala na wiele różnych argumentów:

sub my_sub { 
    SUB: 
    for my $thisarg ($_[0]) { 
    for my $thatarg ($_[1]) { 
     code here sees $thisarg and $thatarg as aliases 
     last SUB; 
    } 
    } 
} 

Oczywiście to przynosi wielopoziomowych zagnieżdżenia i własne problemy czytelności kodu, więc używać go tylko wtedy, gdy absolutnie neccessary.