Perl弱或强类型?

时间:2016-12-09 15:31:39

标签: perl typing

我目前正在从learn.perl.org学习Perl 5,我很好奇它的打字系统。我看到有关Perl弱或强类型的混合信息,并且它也是动态类型的。维基百科声称它也支持鸭子打字。

任何人都可以确认其弱或强类型的性质吗?

2 个答案:

答案 0 :(得分:15)

  

我看到有关Perl弱或强类型的混合信息

这并不奇怪。关于C是强类型还是弱类型语言,也存在相互矛盾的信息。

  • 静态但类型语言的示例是C. [source]

  • C 强烈类型... [source]

  • 这适用于类型的语言,例如C. [source]

  • LISP引擎......本身通常用类型的语言编写,如C ... [source]

  • 使用类型的语言,例如C,... [source]

  • TYPE:强烈输入:(C,Algol,Fortran)[source]

Mark J Dominus compiled上面的列表,discovered有8种不兼容的定义,表明强类型的含义。

  1. 如果类型注释与变量名称相关联,而非使用值,则会强类型化语言。如果类型附加到值,则输入的类型为弱。

  2. 如果语言包含类型约束违规的编译时检查,则强类型语言。如果检查延迟到运行时间,则输入为弱。

  3. 如果语言包含编译或运行时检查,则类型约束违规将被强类型化。如果没有进行检查,则输入结构很弱。

  4. 如果禁止不同类型之间的转换,则会严格键入语言。如果允许进行此类转换,则会进行弱类型转换。

  5. 如果必须明确指出不同类型之间的转换,则会强类型输入语言。如果执行了隐式转换,则会进行弱类型化。

  6. 如果没有语言级别的方法来禁用或规避类型系统,则会强类型语言。如果有演员表或其他类型规避的机制,则输入的类型很弱。

  7. 如果语言具有复合类型的复杂,细粒度类型系统,则会强类型化。如果它只有几种类型,或者只有标量类型,则它是弱类型的。

  8. 如果语言的数据对象的类型是固定的且在对象的生命周期内不变,则会强类型化。如果数据的类型可以更改,则语言键入的类型很弱。

  9. 这表明“强类型”和“弱类型”是meaningless phrases。因此,这个答案的其余部分和所有其他答案实际上只是对你所要求的猜测。

      

    Perl弱或强类型?

    它有强类型(标量,数组,散列等)和弱类型(字符串,浮点数,有符号整数,无符号整数,引用等)。

    这是基于上面列表中的定义#1,#2,#4,#5和#6。

      

    维基百科声称它也支持鸭子打字。

    方法调用使用动态绑定(duck typing)。

    这是明确的。

答案 1 :(得分:5)

如果使用'strong typed'的定义,则意味着您指定变量保存的数据类型 - perl不是。

它基本上有一种类型 - 标量 - 可以容纳各种不同的数据类型。 Perl根据它的“外观”推断操作的正确性。 (它还有散列和数组 - 这是一组标量)

因为你可以:

#!/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";

在字符串和数字之间来回隐式地转换$value,并且它“正常工作” - 我将其称为弱类型。

由于类型不匹配,这些操作......在强类型语言中不起作用(您期望的方式)。

有一点值得一提的是context的概念。 Perl是一种上下文敏感语言,因为它可以从上下文中推断出你的意思。

因此,如果您只是打开并从文件句柄中读取:

open ( my $input, '<', "some_file.txt" ) or die $!;
my $line = <$input>; 

这将从$input读取一行,因为它正在标量上下文中进行读取。

如果您改为:

my @lines = <$input>; 

因为您正在列表上下文中工作,所以文件的整个部分将被读入数组@list

您可以使用wantarray()显式测试上下文(这是一个用词不当 - 它应该是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;

我认为我也认为这是一个弱类型的例子,因为perl 尝试根据上下文找出正确的事情。有时它确实弄错了。

所以你可以:

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";
}

我提到它的原因是(除了注释)上下文也可能被运营商类型强制。

$first .= @second; #forces scalar context due to concat operation.