【问题标题】:What type are Lists of any type in Perl 6?Perl 6 中的任何类型的列表是什么类型?
【发布时间】:2016-01-25 16:24:26
【问题描述】:

考虑以下 Python 代码(作为示例):

a = 5 
b = "a"
l = [a, b] # -> typing.List[typing.Any]
print(l)   
# [5, "a"]

列表l的类型是list;它不受它所拥有的类型的限制,因为 Python 是非常动态的类型。

将其与强结构类型的 Go 进行对比:

var list []uint8{1, 2, 3, 4, 5, 6}

该列表最多只能包含 255 个无符号整数。它不能包含任何其他类型。

也去:

var multi interface{"string", []int{9, 5}, rune('5'), []interface{}}

接口允许使用变体类型的容器。


考虑一下 Perl 6,它比 Python 更具有动态类型,因为 say 6 + "1"; 将给出整数 7。 (谁认为这是个好主意我不知道。)

我喜欢在我的程序中逐渐键入(尤其是对于我正在学习的 Perl 6)它提高了可读性和可维护性。

以下都不是:

use strict;
my Int $n = 6;
my Str $x = "a";
my Int @l = $n, $x;

也没有

use strict;    
my Int $n = 6;
my Str $x = "a";
my List @l = $n, $x;

你会得到Type check failed in assignment to @l; expected List but got Int。 (其他列表构造语法([vals]<vals>)给出相同的错误)。

的作用 说明类型是Any(或Mu),这是有道理的。 (嗯,这对我来说很有意义,因为Any 与 Python 3.5 使用的关键字相同。)

use strict;    
my Int $n = 6;
my Str $x = "a";
my Any @l = $n, $x;

但是首先使用AnyMu 有点违背了类型检查的目的。

如果不是List,列表的类型是什么?此外,如果类型检查永远不会通过任何值或其列表,为什么my List $blah; 是有效语法?

【问题讨论】:

  • 将中缀数字加法运算符+ 用于除数字加法之外的任何内容是一个愚蠢的想法,使用单独的字符串连接运算符更有意义。
  • 您使用的是哪个版本的 Rakudo (perl6 -e 'say $*PERL.compiler')? my Int $n = 6;my Int @l = $n, $n; 对我来说很好用(在 2015.12 之前不要打扰任何事情)。此外,几乎没有理由在 Perl 6 程序中使用 use strict,因为它是默认设置。
  • @BradGilbert 我粘贴了错误的示例。我是rakudo (2015.12.219.gd.67.cb.3),但我现在看到了这个问题的答案。
  • 你可以通过添加一个候选 multi infix:<+> ( \l, Str \r ){ l~r }; say say 6 + "1" 来获得 + 的 Python 行为 => 61␤ 不过不要这样做。
  • @l.WHAT.say 打印出(Array)

标签: list raku


【解决方案1】:

你解释错了,至少 Python 中的 list 与 Perl6 中的 list 不同,它实际上就像 Perl6 中的数组(和 Perl6 list 就像 Python 元组)。

当你这样做时:

my List @l = $n, $n;

you create an array @lenforce all its elements must be 输入List

所以你的第二个例子:

use strict;
my Int $n = 6;
my Int @l = $n, $n;

必须工作。

代码:

my Any @l = $n, $x;

等同于:

my @l = $n, $x;

您已允许数组@l 的元素为任意类型。

【讨论】:

  • 我认为相同的语法告诉对象 是什么 以及 对象的类型是什么的容器 真的很奇怪,但我想我我根本不习惯印记。
  • @cat:如果你读到这个doc.perl6.org/language/containers,你会发现它是合理的。
  • @cuonglm: Nit: aiui,根据现在的测试来验证,my @array ...my Mu @array is default(Any)是一样的。这通常无关紧要,但它可以在重要的时候让事情顺利进行。
  • @cat 实际上没有。当您说my Int $x; 时,您并不是说$x 一个Int,您是说Scalar $x 包含 一个@987654339 @。这对于数组来说更为明显。
【解决方案2】:

如果您希望对列表的元素进行类型检查,则可以使用绑定:= 而不是赋值=

my Int $n =   6;
my Str $x = "a";

# Bind $n and $x to elements of @bound
my @bound := $n, $x;

@bound[1].say;       # Prints "a"
@bound[1] = "Hello"; # Changing the second element changes $x
$x.say;              # Prints "Hello"

@bound[1] = 6; # Dies with error "Type check failed in assignment to $x; expected Str but got Int"

请注意,最后一行创建的错误指的是$x,而不是@bound[1]

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2018-07-05
    • 2020-09-11
    • 1970-01-01
    • 1970-01-01
    • 2010-12-16
    • 2019-08-10
    • 1970-01-01
    相关资源
    最近更新 更多