Mutatók

Perlben minden olyan változó, amely valamilyen skalár, tehát szám, fűzér stb. értéket tartalmazhat; tartalmazhat mutatót is, vagy Perl terminológiával referenciát. A Perl nyelv kétféle referenciát ismer: puha és kemény referenciát. A puha referencia a változók nevén keresztül éri el a tárolt értéket, míg a kemény referencia a változó helyére mutat. Nézzünk egy egyszerű példát:
$alma = 113;
$korte = 'alma';
$szilva = \$alma;
print "$$korte = $$szilva\n";
És az eredményt:
113 = 113

ami egy nagy igazság. Körte egy füzért tartalmaz, és amikor a Perl értelmező a $$körte kifejezést megtalálja, akkor ebből először $alma-t csinál, majd 113-at.

A $szilva változó esetében más a helyzet. Itt a $$szilva kifejezés megtalálásakor a Perl interpreter kiértékeli a $szilva változót, amely egy mutató, amely az $alma változó tartalmára mutat.

Látható, hogy mind a két esetben a referencia használatához a $ jelet kellett a referencia érték elé írni. A mutató létrehozásakor a változó neve elé egy \ jelet írtunk.

Nagyon kényelmes a Perl a memóriakezeléssel kapcsolatban. Nem kell mindenféle malloc, alloc és hasonló függvényeket hívnunk, és nem kell free jellegű memória felszabadító fügvényekkel sem bíbelődnünk. A Perl mindig tudja, hogy mi az amit még használunk, és mi az amit nem. Így akár azt is megtehetjük, hogy

$alma = 114;
sub pointir {
  my $alma = 113;
  return \$alma;
  }

$korte = 'alma';
$szilva = &pointir;
print "$$korte = $$szilva\n";
egy helyi változóra mutató mutatót adunk vissza értékül (C-nél ez teljesen helytelen, és szerencsés esetben core dump a jutalom). A Perl tudja, hogy a létrehozott lokális változóra van hivatkozás és megtartja mindaddig, amíg valamilyen változón keresztül elérhető. Így az eredmény:
114 = 113

Hát ez nem igaz!

Precízebben fogalmazva a lokális változót nem tartja meg a Perl, csak azt a memória helyet, ahol tárolja. Így

sub pointir {
  my $alma = 113;
  return \$alma;
  }

$korte = &pointir;
$szilva = &pointir;
$$szilva++;
print "$$korte < $$szilva\n";
eredménye
113 < 114

Persze nem csak egyszerű változókra lehet mutogatni, ennek nem is lenne sok értelme, hanem tömbökre, hash változókra, függvényekre, meg objektumokra.

Nézzünk egy komplex példát, amiben van minden:

$alma = sub {
  my @alma = (1,1,3);
  return \@alma;
  };
$dinnye  = sub {
  my %alma = (0,1,1,1,2,3);
  return \%alma;
  };

$korte = &$alma;
$szilva = &$dinnye;
$$korte[2]++;
$korte->[2]--;
$$szilva{2}++;
$szilva->{2}--;
for $i (0 .. 2){ print $$korte[$i] }
print ' = ';
for $i (0 .. 2){ print $$szilva{$i} }

aminek eredménye
113 = 113
(Ki gondolta volna!)

A példában $alma és $dinnye két függvényre mutató változó. Az egyik egy tömbre, a másik egy hash-ra mutató mutatót ad vissza értékként. Mind a kettő elérhető a már megismert módon a két $$ használatával is, de elérhetők a tömb, és a hash egyes elemei a C nyelvben megszokott -> operátorral is.


Verhás Péter Home Page . . . . . . Perl röviden, tartalomjegyzék