Custom dumping *in* Data::Dump

After blogging about my small patch to Data::Dump, I contacted Gisle Aas. He is quite responsive and finally comes up with a new release (1.16) of Data::Dump containing the cool new filter feature. My previous example after converted to use the new feature becomes:

$ perl -MData::Dump=dumpf -MDateTime -e'dumpf(DateTime->now, sub { my ($ctx, $oref) = @_; return unless $ctx->class eq "DateTime"; {dump=>qq([$oref])} })'
[2010-06-09T12:22:58]


This filter mechanism is quite generic and allows you to do some other tricks like switching classes, adding comments, and ignore/hide hash keys. The interface is also pleasant to work with, although starting with this release the "no OO interface" motto should perhaps be changed to "just a little bit of OO interface" :-)

Aren't we glad that stable and established modules like this are still actively maintained and getting new features.

Thanks, Gisle!

Effective Perl Programming

I now have my copy of the new edition of Effective Perl Programming. I'm halfway through another book, a wedding on the 20th and some other major personal (good) news, so I won't be able to review it right away. However, a few quick notes:

Pros

  • Covers 5.12.
  • A full chapter on Unicode
  • Good discussion of testing

Cons

  • Recommends SQLite for a test database (I used to like this idea myself).
  • Needs better coverage of Test::Class.

(Can you tell the one chapter I've already read?)

I don't think the testing points are that serious; there needs to be a far more in-depth treatment of testing and for this book, it can't possibly cover this area properly. I also noticed it had nice things to say about Moose, but didn't use it in examples. I think this was the right decision, but I wish it weren't.

And in Web sites it recommends, blogs.perl.org is listed, but use.perl.org is not. Rather interesting.

In any event, those were just a few things I noticed flipping through the book. I'll have a better description later. For now, suffice it to say that it looks very, very good. Just a few of the places I've taken the time to read are well-thought out and show lots of experience.

On Moose default variables

If you read my last post, I was wondering why Moose wasn't accepting array or hash references as default values that could be cloned and, instead, used a code reference to create a new array/hash.

Decided to benchmark the two approaches. The results were... surprising:

Benchmark: timing 500000 iterations of clone, retfunc...
clone: 34 wallclock secs (32.35 usr + 0.12 sys = 32.47 CPU) @ 15398.83/s (n=500000)
retfunc: 4 wallclock secs ( 3.75 usr + 0.02 sys = 3.77 CPU) @ 132625.99/s (n=500000)

With these results, I think the correct behavior is the one already present on Moose, complaining about the default value being an array reference and suggesting an alternative:

References are not allowed as default values, you must wrap the default of 'a' in a CODE reference (ex: sub { [] } and not [])

Decoding HMMs in Perl 6

I've wanted to write a reasonably useful Perl 6 module for a while, and I finally realised that the Viterbi algorithm would be a pretty simple place to start (hopefully it'll be useful as well).

There's a module with the same name on CPAN, but I've based the code on a Common Lisp version I wrote for school a while back. At the moment the module is pretty basic, and doesn't support assigning probabilities to unseen data for example. The module is available on GitHub.

A more advanced version will support computing the sum of the log-probabilities rather than the product, smoothing and unobserved data, and the option of mixing in a role to domain objects so that they can be passed directly to the decode method from the client code.

Smokebrew - It is like perlbrew but different

So, I finally got around to doing what I was threatening to do at Copenhagen and got a tool created to automate the building and configuration of perls for CPAN Testing.

Smokebrew is now available on CPAN and after some smoking of my own dog-food appears to work really really well.

The name was inspired by GUGOD's perlbrew, but Smokebrew itself does things differently to perlbrew.

It doesn't do the environment tweaking, for instance, to switch between the installed perls.

The goal has been to build, install and configure various versions of perl for CPAN Testing.

The configuration is dealt with by App::SmokeBrew::Plugin's. These are objects that are called by Smokebrew after it has successfully built and installed a particular version of perl. Smokebrew comes with two plugins, Null and CPANPLUS::YACSmoke. The former does no configuration and the latter configures for CPAN Testing with CPANPLUS::YACSmoke.

smokebrew --email tester@cpan.org --builddir /home/tester/build --prefix /home/tester/perls --perlargs "-Dusethreads" --perlargs "-Duse64bitint" --plugin Null --recent --verbose

Schorndorf and Ironman

I now officially declare my participation at iron man perly blog sport content after I skope withe a blonde with skirt.

But why I met Matt. Because I'm in schorndorf or course. I's german Perl workshop and my Talks went well. Both of them i will give in Pisa too, in english, and longer. Especially the Rebol talk needs a lot more time I found out. My testing talk was very well recieved. Fine. The Kephra Talk will come tomorrow. All the slides are online now.

Learning Moose - I

Started to look to Moose today. Better later than never. But I never liked OO programming, and Perl core OO was enough for me. So, I am kind of forcing me to do it.

To start with, I am rereading a presentation from Yuval on Portuguese Perl Workshop 2008. I know probably things changed, and so, probably there is a better syntax handling.

At the moment I did not like the way object properties (or variables) are initialized with an array reference:

default => sub { [qw(Bob Alice Tim)] },

I really would prefer it without the sub. Not sure (yet) if if it required or not, but I will find out very soon...

...ahs! Got it, I think. If no sub were supplied, all the objects would get the same reference to the same array. Therefore, the lazy option, and the anonymous function. Well, couldn't that be solved with Clone?

Reviving old code

Recently I've finished rewriting and fixing up Test::SFTP. Version 1.05 and 1.06 were released and they mark the API change and the switch to Test::Builder and Net::SFTP::Foreign.

Test::SFTP is now something I consider "good" and definitely "usable." There's another fix waiting for the next stable release of Net::SFTP::Foreign for some output redirection cleanups. Despite that, it's still good to use.

We all have that code that we put aside completely. At first you assume that you'll get to it sometime, then as time goes by you slowly let go of that idea. Small changes or fixes become tedious and annoying, you hate touching it and at some point you realize you'll probably never work on it again.

There is something joyous in going over that old code and fixing it up, correcting it, finally getting the job done. There's something very motivating in seeing something through to the end.

Read (the perldoc) carefully

Another day in CGI/CGI::Application brought me another question.

My code:

    ... ...
    $out .= $cgi->hidden('rm', 'mode2');
    ... ...
    return $out;

Seems to be OK, just like the example code below, a little bit different though:

$output .= $q->hidden(-name => 'rm', -value => 'mode2');

And if I use a URL like this: "http://www.example.org/cgi-bin/page.cgi?rm=whatever", then the value of the hidden field will now become "whatever".

I thought it was immutable, just like you've written the following line in your code:

$out .= '<input type="hidden" name="rm"  value="mode2"  />';

The truth proved me wrong. So, what's wrong? I decided to read the source code of CGI.pm. Let's walk through the "hidden" subroutine.

sub hidden {
    my($self,@p) = self_or_default(@_);

bless funcion en Perl

Sintaxis

bless REFERENCIA

Accion

Completa una referencia con la indicacion del paquete al que pertenece.

Ejemplo

package CAJA;
{
$var = "333";
$ref = \$var;
$referencia = ref($ref);
}

print $referencia; #imprime ESCALAR

package CAJA;
{
$var = "333";
$ref = \$var;
$referencia = ref($ref);
bless $referencia;
}

print $referencia; #imprime CAJA

Perl, a multi paradigm language

Perl is a great language. Not just because it is flexible, it has a great community, it has Larry Wall as its creator or because it has CPAN. Perl is a great language because it is multi-paradigm. That is, you can write Perl code in different ways, resembling imperative languages, functional languages or object-oriented languages (yes, we can discuss on this division, but that is not relevant at the moment).

What I want to say here is that I love to write functional programming lines with Perl. Check, for instance, on the task of reading a table (tab separated lines) with name, weight and height, and adding a new column with the BMI.

Can you do it on a single functional line?

perl -E 'say join("\n", map {join("\t", addBMI(split /\t/))}
map { s/\n//; $_ } <>);
sub addBMI { push @_, $_[-2]/$_[-1]**2; @_ };' weight.dat

I confess I cheated, defining a new function. Unfortunately push is not functional. Also substitution is not functional at the moment (being prepared on 5.13). Not sure if a functional push version would help. Probably not...

Marpa is now O(n) for Right Recursions

There's news with the latest version of Marpa (0.102000). Marpa now parses grammars with right-recursions in linear time (O(n)). (Marpa already handled left-recursion in linear time.)

This means that Marpa is now O(n) for all LR-regular grammars. LR-regular means LR with infinite lookahead using regular expressions. That a big class of grammars. It obviously includes all the LR(k) grammars, and therefore everything parsed by Yapp, yacc, and bison. LR-regular grammars also include everything parseable by recursive descent, PEGs, and other LL(k) grammars. LR-regular definitely includes all regular expressions.

Marpa's O(n) behavior has another nice feature. When it does not parse in O(n) time, it still parses. Some parser generators always parse quickly, because when they can't parse quickly, they don't parse at all. Marpa will parse anything you can write in BNF, even highly ambiguous grammars, and the absolute worst case is cubic (O(n**3)).

Don't be afraid to use Perl

A long time ago, I wrote this regex to handle a Perl problem I had:

$html =~ s{
             (<a\s(?:[^>](?!href))*href\s*)
             (&(&[^;]+;)?(?:.(?!\3))+(?:\3)?)
             ([^>]+>)
          }
          {$1 . decode_entities($2) .  $4}gsexi;

It didn't work. That not only taught me how to use a proper parser, it led me to write HTML::TokeParser::Simple.

However, some people still insist upon using regular expressions for parsing HTML.

How do you know when you should use a module instead? When the risks outweigh the rewards. Otherwise, go ahead and use that regex. We're here to get jobs done and we should know when is the right time for dogma and when is the right time to extract that href. Don't be afraid to use Perl.

(And when it's a full-blown production system and it's critical that the information is correct, I'll be the first to yell at you for the regex).

ffi_call( 'Wolf!' )

I was pretty excited today because I thought I had my interface for ffi_call working on Linux, and told Twitter and the #soc-help channel all about it. It did seem to be working, until I changed a slight detail in my test script and it became apparent that either there was bewitchery afoot, or I need to read perlxs / perlguts more and it was random change that it hadn't blown up in the first place. I think I'm nearly there though. Next step will be fleshing out the OO functionality in Perl for a bit before diving back into the C for callbacks.

Iron Man Contest

After Matt Trout visit to Portuguese Perl Workshop I got convinced to join this contest. I am not sure if I will maintain my posts in English, or if I join Portuguese from time to time. Just keep visiting.

The last statement

Days ago, I was learning to use CGI::Application.

After finished my baby "run mode", I opened my browser to give it a shot. It worked, and I start wondering why it worked. The last statements of those examples are

return $output;

Mine's not, it looked like this(I forgot to add "return" by accident):

sub run_mode_1 {
    my $self   = shift;
    my $query  = $self->query();
    my $output = q[];
    ... ... 
    $output .= $query->end_html;
}

Como dividir en trozos un texto en Perl

La función split nos sirve para separar por medio de expresiones regulares un string o cadena en varios elementos.

Platform != OS issues

Dear Authors,

Please be aware that you may have received Daily Summaries from the CPAN Testers, that list the archname/platform as i686-linux, but the report in question is from a MSWin32 OS. We are aware of the issue.

Unfortunately, due to an untraditional smoker setup, the tests are run on a Win32 machine, but saved to disk as text files, then parsed on another machine, a i686-linux box, before being submitted to the CPAN Testers servers. As such the metadata sent with the report is misleading, even though the original text report is valid.

As a result, I will be running some validation checks over the weekend on all recent reports (those submitted in 2010) to ensure we have platforms and osnames that correspond with each other. Those that differ will be reparsed and the metadata will be updated accordingly. Further validation checks on incoming reports will also be added to ensure we catch any similar inconsistencies as soon as possible.

Apologies for any confusion.

Thanks,
CPAN Testers.

The Perl Survey is Closed

The Perl Survey 2010 is now closed. A quick preliminary look at the data set indicates that of the 4847 responses, 3256 were complete responses (by looking at who answered the final question). I'm on my way to German Perl Workshop tomorrow, and as I'm coming from Australia, it's going to take me over 24 hours to get there I'll have plenty of time to prepare the data and get a preliminary analysis going during that time.

Most importantly I'll be able to release the (lightly processed) raw data for you by that time as well.

CPAN source syntax highlighting

I've just updated a syntax highlighter bookmarklet I wrote a while back so that it now supports Chrome and Safari, besides Firefox.

I find it useful to syntax highlight when I peek at a module's source code in the CPAN website. You may find it useful too.

To install it, create a new bookmark and paste the following code into the location field (sorry, I couldn't find a way to post this as a javascript: link in this blog):

It will be even handier if you stick it in your bookmark toolbar.

Then view any module's source in CPAN, fire off this bookmarklet and voilà.

I've even thrown in some regex to allow linking from one module to the next. It works 90% of the time, moreless.

The code is actually kept here. There you'll also find a lushier, Alex Gorbatchev's syntax highlighter version available, but I couldn't get it to work in Chrome nor Safari, only in Firefox.

It should be easy to tailor these bookmarklets to fancy your taste buds.

About blogs.perl.org

blogs.perl.org is a common blogging platform for the Perl community. Written in Perl with a graphic design donated by Six Apart, Ltd.