July 2000
Intermediate to advanced
1104 pages
35h 1m
English
If you intend to make use of the object returned from
tie or tied, and the class
defines a destructor, there is a subtle trap you must guard against.
Consider this (admittedly contrived) example of a class that uses a
file to log all values assigned to a scalar:
package Remember;sub TIESCALAR {
my $class = shift;
my $filename = shift;
open(my $handle, ">", $filename)
or die "Cannot open $filename: $!\n";
print $handle "The Start\n";
bless {FH => $handle, VALUE => 0}, $class;
}
sub FETCH {
my $self = shift;
return $self->{VALUE};
}
sub STORE {
my $self = shift;
my $value = shift;
my $handle = $self->{FH};
print $handle "$value\n";
$self->{VALUE} = $value;
}
sub DESTROY {
my $self = shift;
my $handle = $self->{FH};
print $handle "The End\n";
close $handle;
}
1;Here is an example that makes use of our
Remember class:
use strict; use Remember; my $fred; $x = tie $fred, "Remember", "camel.log"; $fred = 1; $fred = 4; $fred = 5; untie $fred; system "cat camel.log";
This is the output when it is executed:
The Start 1 4 5 The End
So far, so good. Let's add an extra method to the
Remember class that allows comments in the
file--say, something like this:
sub comment {
my $self = shift;
my $message = shift;
print { $self->{FH} } $handle $message, "\n";
}And here is the previous example, modified to use the
comment method:
use strict; use Remember; my ($fred, $x); $x = tie $fred, "Remember", "camel.log"; $fred = 1; $fred = 4; comment $x "changing…"; $fred = 5; untie $fred; ...