Which 'Perl Traps' have not been fixed in Raku?

128 Views Asked by At

I was very pleased to find a link to a section called "Perl Traps" in the perldocs. It represents a refreshing sense of honesty in an increasingly tech-hyped world.

The https://perldoc.perl.org/perltrap#Perl-Traps link has 9 bullet points. My question is simple--now that it is 2024--which 'Perl Traps' have not been fixed in Raku?

I feel both Perl users and Raku users want a single SO Question to address all 9 bullets, not 9 SO Questions to address each one individually. Even a scorecard and/or fraction (e.g. 7/9, 8/9, 9/9 would be useful. Thanks.

1

There are 1 best solutions below

0
raiph On

I'm posting this as a community answer because I'm pretty sure it is far from complete.



Remember that many operations behave differently in a list context than they do in a scalar one. … .

"Quoting" a couple comments from the reddit thread "When [Raku] was being designed, what alternatives to expanding context sensitivity were considered?":

  • "[Raku] has nothing like Perl context-sensitivity. Operators don't do different things depending on the surrounding context, and there is no wantarray. … ." 「1」 .

  • "The sort of context sensitivity that sucked in Perl, eg wantarray, was eliminated in Raku. The sort of context sensitivity that was already nice in Perl is even nicer in Raku. … ." 「2」 .

The latter comment was written by me; for more info about the nicer things see the user doc page about contexts in Raku.


Avoid barewords if you can, especially all lowercase ones. You can't tell by just looking at it whether a bareword is a function or a string.

"Quoting" the accepted answer of SO "Rules for barewords":

  • "There are no barewords in [Raku] in the sense that they exist in Perl, and the term isn't used in [Raku] at all. (¶) There are two cases that we might call a "bare identifier": … 「3」 .

(Read the answer for details of the two "bare identifier" cases).


You cannot discern from mere inspection which builtins are unary operators (like chop() and chdir()) and which are list operators (like print() and unlink()).

All routines can be programmatically inspected via .signature, .arity, etc.

Tools can use that to provide relevant human visual inspection ability too.


(Unless prototyped, user-defined subroutines can only be list operators, never unary ones.)

All routines in Raku have signatures (which are Raku's vastly improved take on Perl's deeply problematic "prototypes").


People have a hard time remembering that some functions default to $_, @ARGV, or whatever, but that others which you might expect to do not.

The main replacement for the idea of having to remember a list was to make method invocation without an explicit invocant work for any subroutine or method:

.&say # passes `$_` as the first argument to a `say` subroutine
.say  # passes `$_` as the first argument to a `say` method

One does still have to remember a list, but it's tiny and simple: the matchers (m// and cousins such as s/// and tr///) default to operating on $_.


The <FH> construct is not the name of the filehandle, it is a readline operation on that handle. The data read is assigned to $_ only if the file read is the sole condition in a while loop

Raku's syntax related to file handle usage is conventional, like mainstream PLs.


Remember not to use = when you need =~; these two constructs are quite different: $x = /foo/;, $x =~ /foo/;

Raku replaced =~ with ~~ (a.k.a. 'smart-match', which--despite its seemingly symmetric appearance--acts asymetrically in Raku).


The do {} construct isn't a real loop that you can use loop control on.

Raku produces suitable error messages if a user attempts to use loop controls where they're not valid.


Use my() for local variables whenever you can get away with it (but see perlform for where you can't).

In Raku to clarify scope you're required to use my or our in the first instance of a variable declaration 「4」 . Otherwise, Raku pushed 'formats' outside the core language, so Raku doesn't have this Perl anomaly.


Using local() actually gives a local value to a global variable, which leaves you open to unforeseen side-effects of dynamic scoping.

Raku doesn't have local() (or globals per se).


If you localize an exported variable in a module, its exported value will not change. The local name becomes an alias to a new value but the external name is still an alias for the original.

???