I am currently learning Perl 5 from learn.perl.org and I am curious about its typing system. I see mixed information about Perl being weakly or strongly typed, and that it is also dynamically typed. Wikipedia states that it also supports duck typing.
Can anyone confirm its weakly or strongly typed nature?
I see mixed information about Perl being weakly or strongly typed
That's no surprise given that there is also conflicting information as to whether C is a strongly-typed or weakly-typed language.
An example for a statically, but weakly typed language is C. [source]
C is strongly typed... [source]
This works fine in weakly typed languages such as C. [source]
LISP engines ... are themselves generally written in strongly typed languages like C... [source]
In a weakly typed language such as C, ... [source]
TYPE: strongly typed: (C, Algol, Fortran) [source]
Mark J Dominus compiled the above list, and discovered there are eight incompatible definitions for what it means to be strongly-typed.
A language is strongly typed if type annotations are associated with variable names, rather than with values. If types are attached to values, it is weakly typed.
A language is strongly typed if it contains compile-time checks for type constraint violations. If checking is deferred to run time, it is weakly typed.
A language is strongly typed if it contains compile or run-time checks for type constraint violations. If no checking is done, it is weakly typed.
A language is strongly typed if conversions between different types are forbidden. If such conversions are allowed, it is weakly typed.
A language is strongly typed if conversions between different types must be indicated explicitly. If implicit conversions are performed, it is weakly typed.
A language is strongly typed if there is no language-level way to disable or evade the type system. If there are casts or other type-evasive mechansisms, it is weakly typed.
A language is strongly typed if it has a complex, fine-grained type system with compound types. If it has only a few types, or only scalar types, it is weakly typed.
A language is strongly typed if the type of its data objects is fixed and does not vary over the lifetime of the object. If the type of a datum can change, the language is weakly typed.
This goes to show that "strongly-typed" and "weakly-typed" are meaningless phrases. As such, the rest of this answer and all other answers are really just guesses at what you are asking.
Is Perl weakly or strongly typed?
It has both strong types (scalar, array, hash, etc) and weak types (string, floating point number, signed integer, unsigned integer, references, etc).
This is based on definitions #1, #2, #4, #5 and #6 from the above list.
Wikipedia states that it also supports duck typing.
Method calls utilize dynamic binding (duck typing).
This is unambiguous.
If you use the definition of 'strongly typed' that means you specify what type of data a variable holds - perl isn't.
It basically has one type - scalar - which can hold a variety of different data types. Perl infers correctness of operation based on what it 'looks like'. (It also has hash and array - which are groups of scalars)
Because you can:
#!/usr/bin/env perl
use strict;
use warnings;
my $value = 42;
#concat 0 onto the end.
$value .= 0;
print $value,"\n";
#numeric add
$value += 1;
print $value,"\n";
#division - to create a float.
$value = $value / 4;
print $value,"\n";
#string replacement on a float.
$value =~ s/\.25//g;
print $value,"\n";
Which implicitly casts $value
back and forth between string and number, and it 'just works' - I call it weakly typed.
These are operations that ... wouldn't work (the way you expect) in a strongly typed language because of the type mismatching.
One thing perhaps worth mentioning as related is the notion of context. Perl is a context sensitive language, in that it infers what you mean from the context.
So if you simply open and read from a file handle:
open ( my $input, '<', "some_file.txt" ) or die $!;
my $line = <$input>;
This will read a single line from $input
because it's doing a read in a scalar context.
And if you instead do:
my @lines = <$input>;
Because you're working in a list context, the entirelty of the file is read into the array @list
.
You can explicitly test context using wantarray()
(which is a misnomer - it should really be wantlist
):
#!/usr/bin/env perl
use strict;
use warnings;
use Data::Dumper;
sub context_test {
if ( wantarray() ) {
return ( "some", "results", "here", "(list context)" );
}
else {
if ( defined wantarray() ) {
return "some results (scalar context)";
}
else {
print "called in a void context\n";
}
}
}
my $first = context_test;
print Dumper \$first;
my @second = context_test;
print Dumper \@second;
context_test;
I would I think also call this an example of weak typing, in that perl tries to figure out the right thing to do, based on context. And sometimes it does get this wrong.
So you can:
print "Elements are:", @second, "\n"; # prints elements from the array.
print "Count is", scalar @second,"\n"; #prints number of elements in array.
if ( @second > 2 ) {
print "Array \@second has more than 2 elements\n";
}
The reason I mention it is (aside from a comment) context may also be coerced by operator type.
$first .= @second; #forces scalar context due to concat operation.