[Neworleans-pm] Fwd: Perl 'Expert' Quiz-of-the-Week #20

Brett D. Estrade estrabd at yahoo.com
Thu Jul 29 08:18:17 CDT 2004




=====
http://www.brettsbsd.net/~estrabd

__________________________________
Do you Yahoo!?
Yahoo! SiteBuilder - Free, easy-to-use web site design software
http://sitebuilder.yahoo.com

----- Original message -----
From: "Mark Jason Dominus" <mjd at plover.com>
To: perl-qotw at plover.com
Date: Thu, 29 Jul 2004 07:39:24 -0400
Subject: Perl 'Expert' Quiz-of-the-Week #20




IMPORTANT: Please do not post solutions, hints, or other spoilers
        until at least 60 hours after the date of this message.
        Thanks.

IMPORTANTE: Por favor, no enviéis soluciones, pistas, o cualquier otra
        cosa que pueda echar a perder la resolución del problema hasta
        que hayan pasado por lo menos 60 horas desde el envío de este
        mensaje. Gracias.

IMPORTANT: S'il vous plaît, attendez au minimum 60 heures après la
        date de ce message avant de poster solutions, indices ou autres
        révélations. Merci.

WICHTIG: Bitte schicken Sie keine Lösungen, Tipps oder Hinweise für
        diese Aufgabe vor Ablauf von 60 Stunden nach dem Datum dieser
        Mail. Danke.

BELANGRIJK: Stuur aub geen oplossingen, hints of andere tips in de
        eerste 60 uur na het verzendingstijdstip van dit
        bericht. Waarvoor dank.

VNIMANIE: Pozhalujsta ne shlite reshenija, nameki na reshenija, i
        voobshe lyubye podskazki v techenie po krajnej mere 60 chasov
        ot daty etogo soobshenija.  Spasibo.

Qing3 Zhu4Yi4: Qing3 Ning2 Deng3Dao4 Jie1Dao4 Ben3 Xin4Xi2 Zhi1Hou4 60
        Xiao3Shi2, Zai4 Fa1Biao3 Jie3Da2, Ti2Shi4, Huo4 Qi2Ta1 Hui4
        Xie4Lou4 Da2An4 De5 Jian4Yi4.  Xie4Xie4.

----------------------------------------------------------------

This week's quiz is to write a limited replacement for the CPAN
'MLDBM' module.  The purpose of MLDBM is to allow storage of complex
Perl data structures in a DBM file.

The typical DBM implementation (such as SDBM_File, which comes
standard with Perl) allows the programmer to manipulate a disk
database as if it were an ordinary hash variable.  One says something
like

        tie %hash, 'SDBM_File', $filename;

and thereafter, 

        $hash{"key"} = "value";

stores "value" in the disk file under the key "key", and

        $x = $hash{"key"};

rerieves the value again.  But most DBM implementations are limited to
storing plain strings as values.   Attempting to store undef as a
value actualy stores the empty string instead, so that

        $hash{"key"} = undef;
        print defined($hash{"key"}) ? "oops" : "OK";

prints "oops".  Similarly, attempting to store a compound object such
as 

        [1, 2, 3]

or

        {name => "bill", numbers => [1, 2, 3] }

actually stores a useless string like "ARRAY(0x436c1d)" or
"HASH(0x436c1d)".
Similarly,

        $hash{"this"}{"that"} = "ouch";

causes a "strict refs" failure, if you have "strict refs" checking on,
and a bizarre error if not.  (Sub-quiz: Why?)

The purpose of MLDBM is to work around this.  (See
http://search.cpan.org/~chamas/MLDBM-2.01/lib/MLDBM.pm for complete
details.)  Your task this week is to write a version of MLDBM.  It
should be a tied hash class named 'ML_DBM', such that after

        tie %mldbm, 'ML_DBM', \%hash;

the user can access %mldbm as if it were an ordinary hash, but all
data apparently stored in %mldbm is actually stored in %hash instead.

For example, this must work:

        $mldbm{'array'} = [5,6,7];
        print $mldbm{'array'}[2];    # This must print 7


as must this:

        $mldbm{'hash'} = { I => { like => "pie" } }
        print $mldbm{'hash'}{'I'}{'like'};    # This must print "pie"

and this:

        $mldbm{'a'}{'a2'} = 'AA';
        $z = $mldbm{'a'};
        $z->{'b2'} = "BB";
        print $mldbm{'a'}{'b2'};        # This must print "b2"


There is a trivial solution to this, which is just to store the values
into %hash and fetch them back as requested.  However, this quiz has a
restriction which rules out that solution: The values that ML_DBM
stores in %hash must always be ordinary strings.

The idea is that the user can tie %hash to their favorite DBM
implementation, and then use that as the backing hash for ML_DBM:

        tie %hash => 'NDBM_File', $filename or die ...;
        tie %db => 'ML_DBM', \%hash;

and ML_DBM will (unknowingly, but faithfully) store the data into the
underlying disk file via %hash.  ML_DBM must restrict the values it
stores into %hash to ordinary strings, or else the underlying DBM
implementation (NDBM_File in this case) will not faithfully preserve
them.







More information about the NewOrleans-pm mailing list