[quote=Alex,29.12.2004, 21:12][quote=Strat,29.12.2004, 20:34]aber manche algorithmen werden sehr viel einfacher, wenn man sie mit daten in einer struktur fuettert, bei der sie moeglichst effizient arbeiten.[/quote]
Häh?[/quote]
nimm einfach mal eine subroutine mit parameteruebergabe her; wenn du da z.B. ein @array und einen %hash reingeben willst, bekommt man da probleme:
my @array = 1..10;
my @hash = ('x' => 20, 'y' => 30);
&Sub1(@array, %hash);
sub Sub1 {
my (@array1, %hash1) = @_;
print "@array";
}
Das hat das Problem, dass sowohl @array als auch %hash von @array1 geschluckt werden, und %hash1 leer bleibt. Man koennte da z.B. die laenge von @array als ersten parameter uebergeben und dann die ersten x elemente aus @_ herausfieseln und den rest dann %hash zuweisen:
my @array = 1..10;
my @hash = ('x' => 20, 'y' => 30);
&Sub1($#array, @array, %hash);
sub Sub1 {
my $lastArrayIndex = shift(@_);
my @array1 = @_[0..$lastArrayIndex];
my %hash1 = @_[$lastArrayIndex+1..$
print "@array1";
}
das koennte funktionieren (hab's nicht ausprobiert), ist aber ziemlich umstaendilch. Durch die Verwendung von Referenzen packst du die Daten in ein skalares paektchen, und du hast keinerlei probleme mehr
my @array = 1..10;
my @hash = ('x' => 20, 'y' => 30);
&Sub1(\@array, \%hash);
sub Sub1 {
my ($arrayRef, $hashRef) = @_;
my @array1 = @$arrayRef;
my @hash1 = %$hashRef;
print "@array";
}
in diesem Fall wird die Parameteruebergabe um einiges einfacher (und, wenn du in der subroutine weiter mit den referenzen arbeitest, sparst du auch noch ram, weil die referenz auf die daten von @array bzw. %hash zeigen), und wenn du das element $arrayRef->[4]=300; setzt, wird auch $array[4] auf 300 gesetzt.
ein weiteres beispiel: ein kleines adressbuch:
my %person1 = (name => 'Martin', nick => 'Strat', mail => 'a@local');
my %person2 = (name => 'Alex', nick => 'Alex', mail => 'b@local');
mit sowas kann man wunderbar arbeiten, aber wenn man alle adressen in eine subroutine uebergeben will, kann man zwar jeden einzelnen hash (als referenz) uebergeben, z.B.
&Sub(\%person1, \%person2);
aber sobald eine dritte person dazukommt, musst du das komplette programm aendern. da koennte man z.B. die ganzen personen in eine weitere datenstruktur packen; ich verwende einfach mal einen hash, dessen schluessel die nick's sind und dessen wert ein komplettes personenobjekt
my %addresses = (
Alex => { name => 'Alex', nick => 'Alex', mail => 'b@local' },
strat => {name => 'Martin', nick => 'Strat', mail => 'a@local' },
);
dann hast du das ganze schon mal in einer datenstruktur; wenn du z.B. an eine subroutine nur eine Person uebergeben willst, kannst du das z.B. mit
&Subroutine( $addresses{Alex} )
einfach tun. wenn du aber in der subroutine die infos von mehreren Personen haben willst, kannst du auch die komplette %addresses uebergeben.
habe ich mal fuers erste alle Klarheiten beseitigt?