Beefy Boxes and Bandwidth Generously Provided by pair Networks
Welcome to the Monastery
 
PerlMonks  

Data::Dumper: What the Cabal doesn't want you to know.

by Cow1337killr (Monk)
on May 30, 2023 at 02:26 UTC ( [id://11152489]=perlquestion: print w/replies, xml ) Need Help??

Cow1337killr has asked for the wisdom of the Perl Monks concerning the following question:

3 questions:

  • Can someone please demonstrate a Data::Dumper round trip?
  • Can someone please demonstrate a Data::Dump round trip?
  • Can someone please demonstrate how to print Data::Dumper-like output that is sorted so that it can be used in a diff command in Linux or compare utility program in Windows?

Perl code is fine.

Perl code using CPAN modules is fine.

Thank you for your service.

  • Comment on Data::Dumper: What the Cabal doesn't want you to know.

Replies are listed 'Best First'.
Re: Data::Dumper: What the Cabal doesn't want you to know.
by swl (Parson) on May 30, 2023 at 05:21 UTC

    For #3 have a look at the documentation. $Data::Dumper::Sortkeys is the relevant option in this case.

Re: Data::Dumper: What the Cabal doesn't want you to know.
by choroba (Cardinal) on May 30, 2023 at 08:11 UTC
    Ad 1:
    #!/usr/bin/perl use warnings; use strict; use Data::Dumper; my $struct = [{a => 12, b => 14}, {arr => [5, 6, 7]}]; $Data::Dumper::Sortkeys = 1; my $dump = Dumper($struct); print $dump; my $copy = eval "my $dump"; print Dumper $copy;

    If your structure contains references into itself or code refs, you also need $Data::Dumper::Purity and $Data::Dumper::Deparse. The second one can introduce bugs.

    map{substr$_->[0],$_->[1]||0,1}[\*||{},3],[[]],[ref qr-1,-,-1],[{}],[sub{}^*ARGV,3]
Re: Data::Dumper: What the Cabal doesn't want you to know.
by haukex (Archbishop) on May 30, 2023 at 08:12 UTC

    I'd second SankoR's point about using something like JSON. But for Data::Dumper, see my module Data::Undump::PPI. Data::Dump is a little trickier because its output includes stuff like the range operator, repetition operator, and even MIME::Base64. Of course there's eval, but that's a giant security hole with input that you don't have 100% control over.

Re: Data::Dumper: What the Cabal doesn't want you to know.
by SankoR (Prior) on May 30, 2023 at 03:47 UTC
    Sounds like you're looking for a module to output YAML or JSON. The modules you listed are not intended or designed for use as a configuration store. I'd consider using them that way unsecure at best for that purpose seeing as the simplest solution for restoring the data would be a blind eval.
Re: Data::Dumper: What the Cabal doesn't want you to know.
by LanX (Saint) on May 30, 2023 at 09:53 UTC
Re: Data::Dumper: What the Cabal doesn't want you to know.
by tybalt89 (Monsignor) on May 30, 2023 at 22:53 UTC

    Here's an unasked for but suggested YAML version with round trips and a unified diff in the middle, mainly because I haven't played with YAML for a long, long time.

    #!/usr/bin/perl use strict; # https://perlmonks.org/?node_id=11152489 use warnings; my @animals = (qw( cow camel dog cat )); # slightly changed from 1115 +0326 my @foods = (qw( fish pasture meat )); my @places = (qw( wood sea desert )); my $commands = { select => { completion_list => [@animals], commands => { give => { completion_list => \@foods, }, take_to => { completion_list => \@places, }, }, }, kill => { completion_list => [@animals], } }; use YAML qw( DumpFile LoadFile ); my $originalfile = 'original.11152489'; my $changedfile = 'changed.11152489'; DumpFile $originalfile, $commands; $commands->{select}{commands}{give}{completion_list}[0] .= 'es'; DumpFile $changedfile, $commands; system "diff -u $originalfile $changedfile"; use Data::Dump 'dd'; dd 'original', LoadFile $originalfile; use Data::Dump 'dd'; dd 'changed', LoadFile $changedfile;

    Outputs:

    --- original.11152489 2023-05-30 15:43:38.568028573 -0700 +++ changed.11152489 2023-05-30 15:43:38.571361943 -0700 @@ -9,7 +9,7 @@ commands: give: completion_list: - - fish + - fishes - pasture - meat take_to: ( "original", { kill => { completion_list => ["cow", "camel", "dog", "cat"] }, select => { commands => { give => { completion_list => ["fish", "pasture", "me +at"] }, take_to => { completion_list => ["wood", "sea", "des +ert"] }, }, completion_list => ["cow", "camel", "dog", "cat"], }, }, ) ( "changed", { kill => { completion_list => ["cow", "camel", "dog", "cat"] }, select => { commands => { give => { completion_list => ["fishes", "pasture", " +meat"] }, take_to => { completion_list => ["wood", "sea", "des +ert"] }, }, completion_list => ["cow", "camel", "dog", "cat"], }, }, )
      I haven't played with YAML for a long, long time.

      I have had to work with YAML a bit recently and the one tip I have is that for any dataset beyond the very small indeed, use ingy's excellent YAML::XS instead. Plain YAML is very slow in comparison.


      🦛

Re: Data::Dumper: What the Cabal doesn't want you to know.
by alexander_lunev (Pilgrim) on May 30, 2023 at 16:00 UTC

    Sometime ago I've stumped in a problem that Data::Dumper doesn't show cyrillic symbols correctly, so I write my own dumper:

    use Scalar::Util qw/blessed/; use Data::Dumper; sub pretty { my $self = shift; my $structure = shift; my $depth = shift; $depth = 0 if not defined $depth; $depth += 2; my $string; if (blessed($structure)) { return Dumper($structure); } if (ref $structure eq ref {} ) { # HASH my @arr; foreach my $el (sort keys %{ $structure }) { push @arr, " "x$depth . $el ." => ". $self->pretty($$struc +ture{$el},$depth); } $string .= "HASH { \n" .join(",\n",@arr,undef); $string .= " "x($depth-2) ."}"; } elsif (ref $structure eq ref [] ) { # ARRAY my @arr; foreach my $el ( @{ $structure }) { push @arr, " "x$depth . $self->pretty($el,$depth); } $string .= "ARRAY [ \n" .join(",\n",@arr,undef); $string .= " "x($depth-2) ."]"; } else { $string .= "'".$structure."'"; } return $string; }

    As you can see, I've let Dumper deal with blessed structures, while hashes and arrays printing is done in my way.

Re: Data::Dumper: What the Cabal doesn't want you to know.
by ikegami (Patriarch) on May 30, 2023 at 21:43 UTC

    Data::Dumper is not great at that. Why not use JSON or YAML instead?

      Data::Dumper isn't meant for this, but it can be done.

      use Data::Dumper qw( ); sub serializer { local $Data::Dumper::Purity = 1; local $Data::Dumper::Sortkeys = 1; # Optional, but requested local $Data::Dumper::Useqq = 1; # Optional. return Data::Dumper->Dump( [ $_[0] ], [qw( D )] ); } sub deserializer { my $D; eval( $_[0] ) or die ( $@ ); return $D; } my $text = serializer( $data ); my $copy = deserializer( $text );

      [Woops, this was supposed to be a reply to the OP.]

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://11152489]
Approved by SankoR
Front-paged by Corion
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others imbibing at the Monastery: (3)
As of 2024-04-16 13:48 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found