Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Perl 5.22 and You

Perl 5.22 and You

Ricardo Signes

June 18, 2015
Tweet

More Decks by Ricardo Signes

Other Decks in Programming

Transcript

  1. 5.x

  2. 5.x •every year a new stable perl 5 •each one

    better* than the last •every month a new dev perl 5
  3. 5.x •every year a new stable perl 5 •each one

    better* than the last •every month a new dev perl 5 •each one different than the last
  4. 5.x •every year a new stable perl 5 •each one

    better* than the last •every month a new dev perl 5 •each one different than the last * says me
  5. sigilless style push @array, 1, 2, 3, 4; for (keys

    %hash) { ... } push array, 1, 2, 3, 4;
  6. sigilless style push @array, 1, 2, 3, 4; for (keys

    %hash) { ... } push array, 1, 2, 3, 4; for (keys hash) { ... }
  7. sigilless style push @array, 1, 2, 3, 4; for (keys

    %hash) { ... } push array, 1, 2, 3, 4; for (keys hash) { ... }
  8. hash refauxrence my $value = $hash{key}; $hash{key} = $new; my

    $value = %hash->{key}; %hash->{key} = $new;
  9. hash refauxrence my $value = $hash{key}; $hash{key} = $new; my

    $value = %hash->{key}; %hash->{key} = $new;
  10. ?regex? for (1..10) { say if /./ } for (1..10)

    { say if ?.? } for (1..10) { say if m?.? }
  11. "\cX" "\c@" "\c " "\c牃" "\c¿" "\cX" ==> CANCEL "\c@"

    ==> NUL "\c " ==> GRAVE ACCENT "\c牃" ==> LATIN CAPITAL LETTER X
  12. "\cX" "\c@" "\c " "\c牃" "\c¿" "\cX" ==> CANCEL "\c@"

    ==> NUL "\c " ==> GRAVE ACCENT "\c牃" ==> LATIN CAPITAL LETTER X "\c¿" ==> Hmmm…
  13. ~$ perl -de0 Loading DB routines from perl5db.pl version 1.28

    Editor support available. Enter h or `h h' for help, or `man perldebug' for more help. main::(-e:1): 0 DB<1>
  14. ~$ perl -de0 Loading DB routines from perl5db.pl version 1.28

    Editor support available. Enter h or `h h' for help, or `man perldebug' for more help. main::(-e:1): 0 DB<1> x "\c¿"
  15. ~$ perl -de0 Loading DB routines from perl5db.pl version 1.28

    Editor support available. Enter h or `h h' for help, or `man perldebug' for more help. main::(-e:1): 0 DB<1> x "\c¿" 0 '??'
  16. DB<1> $str = q{"\c} . chr(0xBF) . q{"}; DB<2> $res

    = eval $str; DB<3> x $res That's ¿
  17. DB<1> $str = q{"\c} . chr(0xBF) . q{"}; DB<2> $res

    = eval $str; DB<3> x $res 0 '?' That's ¿
  18. DB<1> $str = q{"\c} . chr(0xBF) . q{"}; DB<2> $res

    = eval $str; DB<3> x $res 0 '?' That's ¿
  19. DB<1> $str = q{"\c} . chr(0xBF) . q{"}; DB<2> $res

    = eval $str; DB<3> x $res 0 '?' DB<4> x ord $res That's ¿
  20. DB<1> $str = q{"\c} . chr(0xBF) . q{"}; DB<2> $res

    = eval $str; DB<3> x $res 0 '?' DB<4> x ord $res 0 255 That's ¿
  21. say $^H; # <-- private compile-time hints say ; #

    <-- private compile-time hints
  22. say $^H; # <-- private compile-time hints say ; #

    <-- private compile-time hints say $爳; # <-- private compile-time hints
  23. p5p conduct •be civil •if you can't be civil, you

    will be escorted out of the building
  24. (<>) while (<>) { print if /awesome/; } $ some-thing

    | your-program $ your-program xyz.txt abc.txt
  25. (<>) while (<>) { print if /awesome/; } while ($ARGV

    = shift) { open(ARGV, $ARGV); while (<ARGV>) { ... } }
  26. (<>) while (<>) { print if /awesome/; } while ($ARGV

    = shift) { open(ARGV, $ARGV); while (<ARGV>) { ... } }
  27. (<>) while (<>) { print if /awesome/; } $ some-thing

    | your-program $ your-program xyz.txt abc.txt
  28. (<>) while (<>) { print if /awesome/; } $ your-program

    xyz.txt 'rm -rfv *|' $ some-thing | your-program $ your-program xyz.txt abc.txt
  29. (<<>>) while (<<>>) { print if /awesome/; } $ your-program

    xyz.txt abc.txt $ some-thing | your-program $ your-program xyz.txt 'rm -rfv *|'
  30. { open my $fh, '>', 'output.txt'; print { $fh }

    $_ for @results; } # $fh is closed implicitly implicit close
  31. { open my $fh, '>', 'output.txt'; print { $fh }

    $_ for @results; } # $fh is closed implicitly # but the disk is full implicit close
  32. { open my $fh, '>', 'output.txt'; print { $fh }

    $_ for @results; } # $fh is closed implicitly # but the disk is full # so the close fails implicit close
  33. { open my $fh, '>', 'output.txt'; print { $fh }

    $_ for @results; } # $fh is closed implicitly # but the disk is full # so the close fails # silently implicit close
  34. { open my $fh, '>', 'output.txt'; print { $fh }

    $_ for @results; } # $fh is closed implicitly # but the disk is full # so the close fails # silently # :-( implicit close
  35. { open my $fh, '>', 'output.txt'; print { $fh }

    $_ for @results; } # warning if close fails! implicit close
  36. { open my $fh, '>', 'output.txt'; print { $fh }

    $_ for @results; } # warning if close fails! # (...and you can fatalize it) implicit close
  37. { use warnings FATAL => 'io'; open my $fh, '>',

    'output.txt'; print { $fh } $_ for @results; } # warning if close fails! # (...and you can fatalize it) implicit close
  38. Avoid Capture qr/v (?<major> [0-9]+ ) ( ( \.[0-9]+ )+

    (?<dev> _ [0-9]+ )? )?/xn; %vers = (major => $+{major}, dev => $+{dev});
  39. Avoid Capture qr/v (?<major> [0-9]+ ) ( ( \.[0-9]+ )+

    (?<dev> _ [0-9]+ )? )?/xn; %vers = %+{ qw(major dev) };
  40. my @array = qw[ foo bar baz quux ]; my

    @slice = @array[ 1, 3 ]; # Now @slice is ("bar", "quux")
  41. my %hash = (a => 1, b => 2, c

    => 3); my @slice = @hash{ 'a', 'c' }; # Now @slice is (1, 3)
  42. my %hash = (a => 1, b => 2, c

    => 3); my %slice = %hash{ 'a', 'c' }; # Now %slice is (a => 1, c => 3)
  43. my %hash = (a => 1, b => 2, c

    => 3); my @slice = %hash{ 'a', 'd', 'a' }; # Now @slice is # (a => 1, d => undef, a => 1)
  44. my @array = qw[ foo bar baz quux ]; my

    @slice = %array[ 1, 3 ]; # @slice is (1 => "bar", 3 => "quux")
  45. my $record = { artist => $album{artist}, title => $album{title},

    tracks => $album{tracks}, year => $album{edition}{year}, label => $album{edition}{lable}, };
  46. my $record = { artist => $album{artist}, title => $album{title},

    tracks => $album{tracks}, year => $album{edition}{year}, label => $album{edition}{lable}, };
  47. my $record = { artist => $album{artist}, title => $album{title},

    tracks => $album{tracks}, year => $album{edition}{year}, label => $album{edition}{label}, };
  48. my $record = { %album{qw( artist title tracks )}, year

    => $album{edition}{year}, label => $album{edition}{label}, };
  49. # Your mission: get a slice of values # from

    $hashref->{x} my $hashref = { x => { ... } };
  50. # Your mission: get a slice of values # from

    $hashref->{x} my $hashref = { x => { ... } }; $hashref->{x}{ k1, k2 } #1
  51. # Your mission: get a slice of values # from

    $hashref->{x} my $hashref = { x => { ... } }; $hashref->{x}{ k1, k2 } #1
  52. # Your mission: get a slice of values # from

    $hashref->{x} my $hashref = { x => { ... } }; $hashref->{x}{ k1, k2 } #1 @{ $hashref->{x} }->{ k1, k2 } #2
  53. # Your mission: get a slice of values # from

    $hashref->{x} my $hashref = { x => { ... } }; $hashref->{x}{ k1, k2 } #1 @{ $hashref->{x} }->{ k1, k2 } #2
  54. # Your mission: get a slice of values # from

    $hashref->{x} my $hashref = { x => { ... } }; $hashref->{x}{ k1, k2 } #1 @{ $hashref->{x} }->{ k1, k2 } #2 @{ $hashref->{x}{ k1, k2 } } #3
  55. # Your mission: get a slice of values # from

    $hashref->{x} my $hashref = { x => { ... } }; $hashref->{x}{ k1, k2 } #1 @{ $hashref->{x} }->{ k1, k2 } #2 @{ $hashref->{x}{ k1, k2 } } #3
  56. # Your mission: get a slice of values # from

    $hashref->{x} my $hashref = { x => { ... } }; $hashref->{x}{ k1, k2 } #1 @{ $hashref->{x} }->{ k1, k2 } #2 @{ $hashref->{x}{ k1, k2 } } #3 @{ $hashref->{x} }{ k1, k2} #4
  57. my $record = { %album{qw( artist title tracks )}, year

    => $album{edition}{year}, label => $album{edition}{label}, };
  58. @{ expr } ⇢ ⇢ ⇢ ⇢ expr->@* %{ expr

    } ⇢ ⇢ ⇢ ⇢ expr->%* ${ expr } ⇢ ⇢ ⇢ ⇢ expr->$* &{ expr } ⇢ ⇢ ⇢ ⇢ expr->&* *{ expr } ⇢ ⇢ ⇢ ⇢ expr->** $#{ expr } ⇢ ⇢ ⇢ ⇢ expr->$#*
  59. @{ expr }[1,2,3] ⇢ expr->@[1,2,3] @{ expr }{k1,k2} ⇢ expr->@{k1,k2}

    %{ expr }[1,2,3] ⇢ expr->%[1,2,3] %{ expr }{k1,k2} ⇢ expr->%{k1,k2} *{ expr }{ARRAY} ⇢ expr->*{ARRAY}
  60. my @array = (1, 2, 3, 4); my $ref =

    \@array; shift @$ref;
  61. my @array = (1, 2, 3, 4); my $ref =

    \@array; shift @$ref;
  62. my @array = (1, 2, 3, 4); my $ref =

    \@array; shift @$ref; say "@array";
  63. my @array = (1, 2, 3, 4); my $ref =

    \@array; shift @$ref; say "@array";
  64. my @array = (1, 2, 3, 4); my $ref =

    \@array; shift @$ref; say "@array"; 2 3 4
  65. my @array = (1, 2, 3, 4); my @copy =

    @array; shift @copy; say "@array"; 1 2 3 4
  66. my @array = (1, 2, 3, 4); \my @alias =

    \@array; shift @alias; say "@array"; 2 3 4
  67. my @array = (1, 2, 3, 4); \my @alias =

    \@array; shift @alias; say "@array"; 2 3 4
  68. my @todo = ({ what => 'eat pie', when =>

    'right now' }, { what => 'eat cake', when => 'quite soon' }); for my $item (@todo) { say "Please $item->{what} $item->{when}." }
  69. my @todo = ({ what => 'eat pie', when =>

    'right now' }, { what => 'eat cake', when => 'quite soon' }); for my $item (@todo) { say "Please $item->{what} $item->{when}." }
  70. my @todo = ({ what => 'eat pie', when =>

    'right now' }, { what => 'eat cake', when => 'quite soon' }); for \my %todo (@todo) { say "Please $item{what} $item{when}." }
  71. fasterization package MyClass { sub new { ... } }

    my $obj = MyClass->new; $obj->UNIVERSAL::isa( ... );
  72. fasterization package MyClass { sub new { ... } }

    my $obj = MyClass->new; $obj->SUPER::new( ... );
  73. ==> x (Inf) 'Inf' ==> x (Inf + 0) 'Inf'

    ==> x (Inf + Inf) 'Inf'
  74. ==> x (Inf) 'Inf' ==> x (Inf + 0) 'Inf'

    ==> x (Inf + Inf) 'Inf' ==> x (Inf - Inf)
  75. ==> x (Inf) 'Inf' ==> x (Inf + 0) 'Inf'

    ==> x (Inf + Inf) 'Inf' ==> x (Inf - Inf) 'NaN'
  76. ==> x (Inf) 'Inf' ==> x (Inf + 0) 'Inf'

    ==> x (Inf + Inf) 'Inf' ==> x (Inf - Inf) 'NaN' ==> x (Inf * 0)
  77. ==> x (Inf) 'Inf' ==> x (Inf + 0) 'Inf'

    ==> x (Inf + Inf) 'Inf' ==> x (Inf - Inf) 'NaN' ==> x (Inf * 0) 'NaN'
  78. ==> x (Inf) 'Inf' ==> x (Inf + 0) 'Inf'

    ==> x (Inf + Inf) 'Inf' ==> x (Inf - Inf) 'NaN' ==> x (Inf * 0) 'NaN' ==> x (NaN + NaN)
  79. ==> x (Inf) 'Inf' ==> x (Inf + 0) 'Inf'

    ==> x (Inf + Inf) 'Inf' ==> x (Inf - Inf) 'NaN' ==> x (Inf * 0) 'NaN' ==> x (NaN + NaN) 'NaN'
  80. ==> x (Inf) 'Inf' ==> x (Inf + 0) '#1.INF'

    ==> x (Inf + Inf) '#1.INF' ==> x (Inf - Inf) '#1.IND' ==> x (Inf * 0) '#1.IND' ==> x (NaN + NaN) '#1.QNAN'
  81. ==> x (Inf) 'Inf' ==> x (Inf + 0) 'Inf'

    ==> x (Inf + Inf) 'Inf' ==> x (Inf - Inf) 'NaN' ==> x (Inf * 0) 'NaN' ==> x (NaN + NaN) 'NaN'
  82. ==> x (0 + "Nan") 'NaN' ==> x (0 +

    "Nancy") 'NaN' ==> x (0 + "123abc")
  83. ==> x (0 + "Nan") 'NaN' ==> x (0 +

    "Nancy") 'NaN' ==> x (0 + "123abc") 123
  84. ==> x (0 + "Nan") 'NaN' ==> x (0 +

    "Nancy") 'NaN' ==> x (0 + "123abc") Argument "123abc" isn't numeric 123
  85. ==> x (0 + "Nan") 'NaN' ==> x (0 +

    "Nancy") 'NaN' ==> x (0 + "123abc") Argument "123abc" isn't numeric 123 ==> x (0 + "Nancy, this is Susan. Susan, this is Nancy.\n\n...") 'NaN'
  86. ==> x (0 + "Nan") 'NaN' ==> x (0 +

    "Nancy") Argument "Nancy" isn't numeric 'NaN' ==> x (0 + "123abc") Argument "123abc" isn't numeric 123 ==> x (0 + "Nancy, this is Susan. Susan, this is Nancy.\n\n...") Argument "Nancy, this is Susan... 'NaN'
  87. hex floats $x = 0xE.A3p4; # 234.1875 printf "%x", $x;

    # "ea" printf "%a", $x; # 0x1.d46p+7
  88. hex floats $x = 0xE.A3p4; # 234.1875 printf "%x", $x;

    # "ea" printf "%a", $x; # 0x1.d46p+7 :-)
  89. sub add ( $x = (return 0), $y = return

    $x + do { my $dbh = DBI->connect($DSN); my ($y) = $dbh->selectrow_array( "SELECT rhs FROM op_defaults WHERE op = '+'" ); $y } ) { return $x + $y; }
  90. sub process_queue { my ($self, $arg, $queue) = @_; for

    my $item ( @$queue ) { debug($item->{name}) if $arg->{debug}; $self->accept($item->{job_id}); } }
  91. sub process_queue ($self, $arg, $queue) { for my $item (

    @$queue ) { debug($item->{name}) if $arg->{debug}; $self->accept($item->{job_id}); } }
  92. sub process_queue ($self, $arg, $queue) { for \my %item (

    @$queue ) { debug($item{name}) if $arg->{debug}; $self->accept($item{job_id}); } }
  93. sub process_queue ($self, $arg, $queue) { for \my %item (

    @$queue ) { debug($item{name}) if $arg->{debug}; $self->accept($item{job_id}); } }
  94. sub process_queue ($self, \%arg, \@queue) { for \my %item (

    @queue ) { debug($item{name}) if $arg{debug}; $self->accept($item{job_id}); } }
  95. strictures use strict; while ( my $event = next_event )

    { print { $logfile } "$event\n"; }
  96. strictures use strict 'stringification'; while ( my $event = next_event

    ) { print { $logfile } "$event\n"; } Can't stringify a reference with no overloading while "strict stringification" in use