2010-10-07 17 views
6

W jaki sposób łączysz tablice aliasów w Perlu tak, aby wynikowa tablica zawierała również aliasy?Jak mogę łączyć tablice aliasów w Perlu?

Rozwiązanie, które wymyśliłem to:

my ($x, $y, $z) = 1 .. 3; 

my $a1 = sub {\@_}->($x); 

my $a2 = sub {\@_}->($y, $z); 

my $a3 = sub {\@_}->(@$a1, @$a2); 

say "@$a3"; # 1 2 3 

$_++ for $x, $y, $z; 

say "@$a3"; # 2 3 4 

Co nie jestem szalony o to, że aby stworzyć $a3 muszę całkowicie rozpakować $a1 i $a2. W przypadku krótkich tablic nie stanowi to problemu, ale wraz z rosnącymi danymi oznacza to, że wszystkie operacje tablicowe na tablicach z aliasami to O(n), w tym operacje tradycyjnie , takie jak push lub unshift.

Data::Alias może pomóc, ale nie działa z najnowszymi wersjami Perla. Array::RefElem zawiera opakowania wokół aproksymatorów api av_store i av_push, których można użyć do zaimplementowania tej funkcji. Tak więc coś takiego może zadziałać:

sub alias_push (\@@) { 
    if (eval {require Array::RefElem}) { 
     &Array::RefElem::av_push($_[0], $_) for @_[1 .. $#_] 
    } else { 
     $_[0] = sub {\@_}->(@{$_[0]}, @_[1 .. $#_]) 
    } 
} 

Chciałbym wiedzieć, czy są jakieś inne sposoby. Szczególnie, jeśli istnieją inne sposoby wykorzystania tylko podstawowych modułów.

+1

Myślę, że "fix Data :: Aliasy" może być najlepszą (choć może nie najszybszą) drogą. :) – Ether

+0

@Ether => Czy masz pojęcie, jak głębokie są niezgodności? –

+0

@Eric: nie, chociaż podejrzewam, że ktoś musi znaleźć tuit, aby go przenieść do korzystania z powiązań API 5.12. – Ether

Odpowiedz

1

Czy jest to jeden z przypadków, w których może być pożądana lista połączonych w Perl? Steve Lembark has a talk o różnych przypadkach, w których ludzie powinni ponownie rozważyć rozwijanie i rozwijanie tablic.

Jestem ciekawy, dlaczego musisz robić to w ten sposób. Nie dlatego, że podejrzewam coś dziwnego; Jestem tylko ciekawy problemu.

+0

Lista połączona może być dobrym rozwiązaniem, ładnie omija problemy z literą "O (n)". Aplikacja, którą mam na myśli, to symulować Haskella jak leniwe zachowanie w Perlu (głównie dlatego, że myślę, że mogę :), chciałbym w końcu napisać coś takiego w Perlu: 'fibs = 0: 1: zipWith (+) Fibs (tail fibs) 'i część tego jest zarządzanie listami argumentów, które mogą zawierać wartości, które nie zostały jeszcze zdefiniowane (ale będą do czasu, kiedy będą potrzebne) –

+0

Och, w takim przypadku, poczekaj rok i użyj Perl 6 Leniwe listy to jedna z najbardziej atrakcyjnych funkcji dla mnie. :) –

+0

@Eric, @brian, a może Perl 5.1x? (gdzie x> 2 i x || 2) – Axeman