Perl6:子条款中的构造函数

Mik*_*kel 5 constructor perl6

有没有办法从子类中的构造函数分配超类中声明的实例变量?我已经习惯使用BUILD()作为构造函数,但我想知道这是不是一个好主意.即:

use v6;      

class File                                                                                                                                                                                                                                    
{                                                                                                                                                                                                                                             
    has $!filename;                                                                                                                                                                                             
}                                                                                                                                                                                                                                                                                                                                                                                                                                                                                       

class XmlFile is File                                                                                                                                                                                                                         
{                                                                                                                                                                                                                                             
    submethod BUILD(:$!filename)                                                                                                                                                                                                              
    {
    }
}

my XmlFile $XF = XmlFile.new(filename => "test.xml");
Run Code Online (Sandbox Code Playgroud)

上面的代码不起作用,提示错误:"属性$!filename未在类XmlFile中声明".这是使用正确的访问者的问题吗?改变"!" 至 "." 没有解决问题.

Eli*_*sen 4

你已经成功一半了。您必须对代码进行正确的两项更改:

class File {
    has $.filename;                   # 1. Replace `!` with `.`
}

class XmlFile is File {
    submethod BUILD(:$filename) { }   # 2. Remove `!`
}

dd my XmlFile $XF = XmlFile.new(filename => "test.xml");

# XmlFile $XF = XmlFile.new(filename => "test.xml")
Run Code Online (Sandbox Code Playgroud)

在类中替换$!filename为会在该类中生成一个公共访问器方法 ( )。$.filenameFile.filename

(请注意,从技术上讲,属性对于类始终是私有的,即始终对其他类(甚至是受信任的类)不可用。当您看到短语“公共属性”时,它实际上意味着存在一个“公共访问器”,它控制对相应的底层私有属性的访问.)

从类的签名中删除!twigil意味着您不再尝试引用不存在的属性,而只是传递命名参数。BUILDXmlFileXmlFile

每个对象构造

由于 BUILDALL 和 BUILD 子方法的默认行为,派生的构造函数的命名参数new可以Mu直接对应于方法解析顺序中任何类的公共属性,或任何 BUILD 子方法的任何命名参数。

(“公共属性”用词不当。它的意思是“具有匹配的公共访问器的属性”。)