タイトル

Synopsis 12:オブジェクト

著者

Larry Wall <larry@wall.org>
 

機種

Created: 27 Oct 2004

Last Modified: 19 Sep 2011
Version: 123
 

概観

この概要はオブジェクト指向のプログラミングを論じる Apocalypse 12を要約する。

クラス

クラスが宣言されたモジュールであるでclass キーワード。 モジュールと同じように、クラスの公共の記憶域、インタフェースと名前はパッケージと通常であるその名前によって表される(ただ必ずしも)グローバル名. クラスはモジュールであって、そしてそれで内容を書き出すことができる、しかしクラスが Perl 6 のスタンダードクラス・ベース OO をサポートするためにもっと多くの振る舞いさえ加える。

型と思われて、オブジェクト、クラス名がその型の可能な値のすべてを表す、そして型オブジェクトはそれでその型のノーブランドオブジェクトが何をすることができるか計算することにおいてその型のどんな「実数」オブジェクトでもの代理人として使われることができる。 クラスオブジェクトはオブジェクトだ、しかし、 Perl 6 に義務的なクラスクラスがないために、そして型オブジェクトが Perl 6 に未定義であると見なされるために、それはクラスじゃない。 我々はクラス・ベースとプロトタイプベースの OO プログラミング両方をサポートすることを望む。 それですべての metaprogramming することは現在のオブジェクトのを通してされるHOW それが好きである metamodel に何にでも metaprogramming を委任することができるオブジェクト。 しかしながら、デフォルトによってで、オブジェクトによって得られたからMu かなり標準的なクラス・ベースモデルをサポートしろ。

2つの基本クラス宣言シンタクスがある:

class Foo;          # rest of file is class definition
has $.foo;

class Bar { has $.bar }     # block is class definition
 

最初のフォームがただコンパイル単位で最初の宣言として許される(すなわち、ファイルあるいは eval 文字列)。

もしクラス体がその主な演算子がシングルである文から始まるならprefix:<...> (yada)リスト演算、クラス名は定義なしで開始される、そして同じ範囲でそのクラスの2番目の宣言が再定義について不平を言わない。 (文修飾子がそんなものに入ることを許される... 演算子。) それであなたはあなたのクラスをフォワード - 宣言してもよい:

class A {...}     # introduce A as a class name without definition
class B {...}     # introduce B as a class name without definition

my A $root .= new(:a(B));

class A {
    has B $.a;
}

class B {
    has A $.b;
}
 

この例が示す(とき・から・につれて・ように)、(もちろん、それが回帰的な継承を許すことができないけれども)、これは相互に回帰的なクラス定義を可能にする。

クラスを延長することは同じく可能であるとしてaugment 宣言詞、しかしそれはいくぶん反社会的であると見なされて、そして先付け宣言のために使われるべきじゃない。

[推測:我々は同じく許すかもしれないproto そしてmulti 多数の死体が意図的に一つの定義に参加するという状態で、明示的にクラスだと宣言するべきクラス定義に関する宣言詞修飾子。]

名指されたクラス宣言がただ名指されたサブルーチン宣言のように、展開式の一部として起こることができる。

クラスは主に、コード再利用ではなく、マネージメント例えば。 あなたがただ共通コードを要因から外すことを望むとき、ロールを使って見なせ。

Perl 6 は多数の継承、匿名のクラスとオートボクシングをサポートする。

公共のメソッドが呼び出すすべてが C++ センスで「バーチャルだ」。

あなたは何からでも組込み型を得てもよい、しかし低レベルの型の導出は好むint ただ行動を加えて、代表を変えないかもしれない。 作文そして/あるいは代表団を代表を変えるために使え。

Perl 6 に barewords がないから、そのままの class name が前もって宣言されなくちゃならない。 あなたはあなたがサブルーチンに対してそうするであろうのとちょうど同じように切り株クラスを前もって宣言して、そして後にそれを記入することができる。

クラスとしての名前あるいは使っている型名の権限:力解釈:: 接頭辞。 右辺値コンテキストで:: 接頭辞は無操作命令だ、しかし declarational コンテキストで、それは、他の何宣言によっても宣言されるという状態で、前方へ宣言のスコープの中の新しい型名をバインドする。

なしにmy あるいは宣言詞をスコープ宣言している他そのままclass 宣言詞が宣言するour 宣言詞、すなわち、現在のパッケージの中の名前。 ファイルが解析をし始めるクラスからGLOBAL パッケージしろ、ファイルで最初のクラス宣言はそれ自身をグローバル名としてインストールする、そして次の宣言がそれから、グローバルなパッケージよりむしろ現在のクラスへと(彼・それ)ら自身をインストールする。

従って、現在のパッケージ(あるいはモジュール、あるいはクラス)で内部のクラスを宣言するために、使えour class あるいはただclass.  レキシカルにスコープ宣言されたクラス、使用を宣言するためにmy class.  名前が最も外側で常にへ一番奥のスコープから捜されるクラス。 イニシャルと同じように::プレゼンスの:: 名前以内は(Perl 5 の場合と異なり) globalness を暗示しない。 それで外へ向かう捜索は検索済みネームスペースの子供たちに見ることができる。

クラストレイト

トレイトが使ってセットされるクラスis

class MyStruct is rw {...}
 

一つの継承

「isa」はただたまたまもう1つのクラスであるトレイトに過ぎない:

class Dog is Mammal {...}
 

多数の継承

多数の継承が複数で指定されるis 修飾子:

class Dog is Mammal is Pet {...}
 

作文

ロールが使うdoes 代わりにis

class Dog is Mammal does Pet {...}
 

also 宣言詞

あなたは使用によって同様に内部にこれらを入れるかもしれないのalso 宣言詞:

class Dog {
    also is Mammal;
    also does Pet;
    ...
}
 

(しかしながら、also 宣言詞が主にロールでの使用のために、問題のトレイトが落ち着いたクラスによりむしろ直接ロールに適用されるはずであるという偽の印象を伝える傾向があるロールヘッダーに入れられるとき適切に一般的であると解釈されないかもしれないクラストレイトを区別するように意図される。)

Metaclasses

すべてのオブジェクト(何でも含めてクラス・ベースオブジェクト)がそのメタクラスの例に権限を委ねる。 権限:が何のメタクラスででもオブジェクトを得るとしてHOW メタクラスの例を返すメソッド。 「クラス」オブジェクトが Perl 6 にちょうど「空の」インスタンスだと見なされて、いっそう適切に「プロトタイプ」と呼び出される、あるいは「ノーブランド」オブジェクト、あるいはただ「タイプのオブジェクト」。 Perl 6 は本当にクラスが名前をつけた何も持っていないClass.  そうなこれらの未定義の型オブジェクトとしてのタイプの種類がその代わりに指命されるすべてが見なした、から themsleves のインスタンスを作られたバージョンとまったく同じ型を持て。 けれどもこのような型オブジェクトは不活発であって、そしてクラスインスタンスについてステートを管理しない。

インスタンスを管理する実際のオブジェクトは通り過ぎて指し示されたメタクラスオブジェクトであるHOW 構文。 あなたが言うときそう「Dog」あなた両方ともにパッケージを知らせているそしてどちらかのオブジェクト、後者がとしてクラスを表しているオブジェクトを指し示す型HOW.  型オブジェクトは、異なった型を持つことによって、ではなく、むしろそれが定義される程度でインスタンスオブジェクトとは違う。 若干のオブジェクトが教えるかもしれない、あなたそのそれらは定義される、他方他のものが教えるかもしれない、あなたそのそれらは未定義だ。 オブジェクト次第であって、そして、メタクラスがどのようにディスパッチに選択するかについて、依存する.defined メソッド。

注釈^Dog 構文的な構文糖は賛成だDog.HOW()それで^ あなたが現在のメタクラスの例について話をすることを望むとき、「クラス」シギルだと見なされることができる。

閉じたクラス

クラスはデフォルトまでに開いていて、そして最終じゃない、しかし容易に、誰も公開されているか、あるいは最終じゃない状態でクラスが留まるという明示的なコンパイル時のリクエストを表示しなかったなら、(彼・それ)らだけでではなくアプリケーション全体によって閉じられるか、あるいは完成させられるかもしれない。 (あるいはサイトポリシーがポリシーを使うどんなアプリケーションでも閉じることができた。) しかしながら、 sub - アプリケーションのダイナミックな荷積みをするプラットホームがおそらく卸売りでクラスを閉じるか、あるいは完成させることを望まない。

ロールが閉じたクラスのコンパイル時関数のいくらかを雇う、それであなたはとにかくその代わりにおそらくそれらを使うべきだ。

私立クラス

私立クラスが使うと宣言されることができるmy問題が Perl 6 にスコープ宣言して語彙で扱われるたいていのプライバシー。 輸入が同じくデフォルトまでに語彙であるという事実は何でも輸入が同じく私的なあなたのクラスをデフォルトと命名することを意味する。

クラス作文

(特に、ロール構成)がそうであるクラス宣言が厳密に時間文をコンパイルする。 特に、もしクラス宣言がネストされた有効範囲の中に現われるなら、クラス宣言はまったく同じように何に関してでも死刑の可能性を構成することを強制される。 ロールとスーパークラスという名前のすべては非 rebindable 読み取り専用値としてバインドされなくちゃならない;ただ非クローニングのコンテキストでとトレイトへのパラメータがであろう何でも評価した。 クラス宣言によってバインドされた名前が非 rebindable にされて、そして、ただそれらがスーパークラスとして使用されるかもしれないようにだけ、読まれる。

匿名のクラス宣言

匿名のクラス宣言で、:: ひとりでに、もし望ましいなら、匿名のクラス名を表すかもしれない:

class {...}                # ok
class is Mammal {...}      # WRONG
class :: is Mammal {...}   # ok
class { is Mammal; ...}    # also ok
 

メソッド

メソッドがクラスに宣言された定常課程であるでmethod キーワード:

method doit ($a, $b, $c) { ... }
method doit ($self: $a, $b, $c) { ... }
method doit (MyName $self: $a, $b, $c) { ... }
method doit (::?CLASS $self: $a, $b, $c) { ... }
 

Invocants

インボカントの宣言はオプションだ。 あなたは常にキーワードを使って現在のインボカントにアクセスしてもよいself.  もちろん実際の(事実上の)型が語彙の型の派生型であるかもしれないけれども、あなたはインボカントの語彙のクラスが、メソッドがインボカントのクラスに宣言されなくちゃならないから、とにかく知られているから、インボカントの型を宣言する必要がない。 あなたはいっそう制約が多い型を宣言することができた、しかしそれはおそらく適切な多様性のために良くないことだろう。 あなたは離れて最適化されるであろう型、しかし何でも調べる語彙で明示的にインボカントをタイプしてもよい。 (レキシカルに決定されたクラスが常に名前をつけられるかもしれない流れ::?CLASS 匿名のクラスでさえ、あるいはロール。)

明示的なインボカントに記録を残すために、ただそれの後にコロンを置け:

method doit ($x: $a, $b, $c) { ... }
 

もしあなたが配列変数を使って配列のための明示的なインボカントを型だと宣言するなら、あなたはそれを直接リストコンテキストでその要素を作り出すために使うかもしれない

method push3 (@x: $a, $b, $c) { ... any(@x) ... }
 

それに注意するself 敏感な、そして次の通りの関数ではないコンテキストが常にリストコンテキストでさえ一つの品目として現在のオブジェクトを返す。 従ってもしあなたの現在のオブジェクトがたまたま配列である、しかしあなたがそれを宣言しなかったなら、明示的な配列変数で、あなたはどうにかして明示的に配列の要素にアクセスする必要がある:

any(self)     # WRONG
any(self[])   # okay
any(@(self))  # okay
any(@self)    # WRONG unless you declared @self yourself
 

私的なメソッド

私的なメソッドが使うと宣言される!

method !think (Brain $self: $thought)
 

(このようなメソッドは完全に普通のメソッド呼び出しに見えなくて、そして実際使う異なった構文で呼び出される! の代わりに. 文字。 下を見ろ。)

メソッド有効範囲規則

他のほとんどの宣言と異なり、method 宣言がデフォルトではなくをそうしないためにするour 意味規則、あるいはさらにmy 意味規則、しかしどちらかと言えばhas 意味規則。 それで、語彙あるいはパッケージシンボルテーブルの中にシンボルをインストールする代わりに、それらがそのメタオブジェクトにただ公共あるいは個人のメソッドを呼び出しとしての現在のクラスあるいはロールにインストールする。 (同じく賛成だsubmethod 宣言 - 下に Submethods を見ろ。)

明示の使用has 宣言詞が宣言に影響を与えない。 あなたは追加のエイリアスをメソッドにレキシカルスコープ使用方法にインストールしてもよいmy あるいは現在のパッケージ使用方法でour.  別名が一緒に名前をつけられるこれら&foo 表記法と帰りRoutine サブルーチンとして、呼び出されるかもしれないオブジェクト、その場合あなたは最初の引数として期待されたインボカントを供給しなくちゃならない。

メソッド呼び出し

普通のメソッド - ディスパッチ意味規則で普通のメソッドを呼び出すために、ドット表記法あるいは間接的なオブジェクト表記法を使え:

$obj.doit(1,2,3)
doit $obj: 1,2,3
 

たとえコロンの後に引数がないとしても、間接的なオブジェクト表記法がインボカントの後に今コロンを必要とする:

$handle.close;
close $handle:;
 

メソッド呼び出しを拒絶して、そしてただ見なすためだけに、 sub が、ただ援用ラインからコロンを除く:

close($handle);
close $handle;
 

しかしながら、ほらクラスが定義する組込み IO method close () is exportどの投げかmulti sub close (IO) デフォルトのそばに範囲で。 それでもし$handle evaluates から an IO 上のサブルーチン呼び出しがそうであるオブジェクト、それから2(人・つ)がまだ呼び出しをメソッドに翻訳した。

もしそれが入っているなら、ドット表記法がインボカントを除くことができる$_

.doit(1,2,3)
 

メソッドが呼び出しだと想像する

私的なメソッドのために対応する注釈がないことに注意を払え。

!doit(1,2,3)        # WRONG, would be parsed as not(doit(1,2,3))
self!doit(1,2,3)    # okay
 

メソッド名のために間接参照のいくつかのフォームがある。 あなたは識別子を引用文字列で置き換えることができる、そして、クォートそして次にそれの結果がメソッド名として使用される(とき・から・につれて・ように)、それは評価されるだろう。

$obj."$methodname"(1,2,3)   # use contents of $methodname as method name
$obj.'$methodname'(1,2,3)   # no interpolation; call method with $ in name!

$obj!"$methodname"()          # indirect call to private method name
 

Perl 5 brainos を捕えることへの支援として、この引用されたフォームは常に括弧で括られた引数リストがそれを Perl 5 結合のように見えるコードから区別することを必要とする。

書き入れの中で、二重に引用された書式は空白文字を含まないかもしれない。 これは期間で終わって引用された文字列についてユーザーが共通で期待するものに場合をする:

say "Foo = $foo.";
 

もしあなたが本当に空白文字でメソッドを呼び出すことを望むなら、あなたはクロージャ書き入れでこの制限に取り組んでもよい:

say "Foo = {$foo."a method"()}";  # OK
 

[注意しろ:間違った(人たち・もの)が使うキャッチを助けるためにinfix:<.> 文字列として、もしクォートの中の文字列が識別子であるなら、6が「クォートの役に立たない使用」についてあなたに警告するであろう連接演算子、 Perl は時間をコンパイルする。 (それは非識別子について文字列が欠けているメソッドエラーを作り出す可能性が高い文字列、しかしそんなものが何での時間にも場合の負担を強いることを警告しない。) 同じく、もし婚約者の周りに空白文字があるなら. 結合、それはまったくメソッド呼び出しと解析されることができない;その代わりに、スタンダード Perl 6 がそうしたから、それはコンパイル時間に失敗する擬似infix:<.> 常にコンパイル時間に失敗する演算子。]

あなたがすでにメソッドを位置しているようにする状態のために、あなたはメソッド名前:の代わりに単純なスカラー変数を使うことができる

$methodobj = $foo ?? &bar !! &baz;
$obj.$methodobj(1,2,3)
 

あるいはいっそう簡潔にしかしより低度に読めるように:

$obj.$($foo ?? &bar !! &baz)(1,2,3)
 

変数不可欠を含む段落Callable オブジェクト(通常型についてCode)、すなわち、ある種のクロージャ. クロージャがメソッドあるいは sub と定義された、あるいはブロック、クロージャが何かなしで直接呼び出されるかどうかにかかわらず、ディスパッチを分類しろ; しかしながら、クロージャの見地から、それは、オブジェクトをその最初の引数と第2の引数、サード、などの残りとして、常にメソッドと呼び出される。 例えば、このようなクロージャは後にパス耕起のルートを指定しないでデータ構造を通して「ナビゲーションの」パスを要約するために使われるかもしれない:

$locator = -> $root, $x, $y { $root.<foo>[$x]<bar>{$y}[3] }
$obj.$locator(42,"baz")  # $obj<foo>[42]<bar><baz>[3]

$locator = { .<here> }
$obj.$locator            # $obj<here>
 

都合が良い形のドキュメンテーションとして、このようなクロージャは同じく匿名のメソッドのかたちで書かれるかもしれない:

$locator = method ($root: $x, $y) { $root.<foo>[$x]<bar>{$y}[3] }
$obj.$locator(42,"baz")  # $obj<foo>[42]<bar><baz>[3]

$locator = method { self.<here> }
$obj.$locator            # $obj<here>
 

注意するしかしながら何のようにでも匿名のクロージャ、匿名のメソッドがただディスパッチされることができるだけであること、から直接、 sub が好きだ。 あなたは、もちろん、クラスの公共のインタフェースのメソッド、それがどちらのケースにもう匿名じゃなくて、そしてディスパッチされるかもしれないかの名前へのから通常クラスとしての匿名のメソッドをバインドするかもしれない。 (そして実際標準のメソッドディスパッチャーがその候補者リストで個々の候補者を呼び出しているとき、それは、メソッドとしてではなく、 sub としてそれぞれの候補者を呼び出す、あるいはあなたは回帰的なディスパッチャーで終わるだろう。) けれども基本的に、メソッドクロージャなどというものはない。 method 匿名のメソッドの上の宣言詞がインボカントの宣言をオプションにする主要な効果を持っている。 (それは同じくそれを当局者にするRoutine 返されることができるから、ただ、あなたが使ったかのようにsub それを宣言するために。)

スカラー変数の代わりに、配列変数が同じく使われるかもしれない:

$obj.@candidates(1,2,3)
 

スカラー変形と同じように、文字列メソッド名が許されない、ただCallable オブジェクト、リストは呼び出すべき候補のリストとして取り扱われる。 最初の成功した呼び出しの後に候補の残りが捨てられる。 現在の候補の失敗が、呼び出すことによって、示されるnextwith あるいはnextsame (下にメソッドのセットを呼び出すことを見ろ)。

同じくそれに注意する

$obj.$candidates(1,2,3)
 

フォームがもしを候補のリストに緊急派遣するかもしれない$candidates リストあるいはスペシャルだCode 候補のリストに部分的なディスパッチを表しているオブジェクト。 もし$candidates (あるいはどんな要素でもの@candidates)それが回帰的に拡張されたアウトである iterable オブジェクトだCallable 候補が見いだされる。 呼び出しは、もしそれが候補者をぶつならそのではないに失敗するCallableIterableあるいはList.

もう1つの間接参照の形式が演算子があなたにこれらのフォームを与えるペア表記法で変形を使って名指されるという事実に頼る:

$x.infix:[$op]($y)
$x.prefix:[$op]
$x.postfix:[$op]
 

一般にあなたは添え字のリテラルの角括弧フォームでこれらを見る:

$a.infix:<*>($b)      # equivalent to $a * $b
$a.prefix:<++>        # equivalent to ++$a
$a.postfix:<++>       # equivalent to $a++
 

もしあなたが構文カテゴリを省略するなら、呼び出しは、「接頭辞」としてあるいは「インフィックス」として引数の数によれば、ディスパッチされるだろう:

$a.:<+>($b)           # equivalent to $a + $b
$a.:<++>              # equivalent to ++$a
$a.:<!>               # equivalent to !$a
@a.:<[*]>             # equivalent to [*] @a
 

けれども、実際の演算子が明白じゃないとき、構文カテゴリを説明するほうがおそらく良い:

$x.infix:[$op]($y)
$x.prefix:[$op]
 

あなたは特別な構文を私的なメソッドを呼び出すために使わなくちゃならない:

$mybrain!think($pinky)
self!think($pinky)
 

呼び出しの間あなた自身の私的なメソッドに、あなたは同じく attribute-ish 形式を使ってもよい:

$!think($pinky)     # short for $(self!think($pinky))
 

括弧(あるいはコロン)がきっかり必要とされて / 、もし引数があるなら(副詞の引数を計算に入れないで)、表記をバンと鳴らす。 あなたが「unspace」を利用しないなら、メソッド名と左の括弧の間にスペースがないかもしれない:

.doit       # okay, no arguments
.doit()     # okay, no arguments
.doit ()    # ILLEGAL (two terms in a row)
.doit\ ()   # okay, no arguments, same as .doit() (unspace form)
 

名指されたメソッド呼び出しフォームが特別であるとは、注意しろ、そして接尾辞のドットフォームを使うな。 もしあなたがフォーム、それがあなたが引数がないメソッドを呼び出して、そして次にそれの結果を呼び出すことを望むと想定するであろう後置演算子を使おうと試みるなら:

.doit.()    # okay, no arguments *twice*, same as .doit().()
.doit\ .()  # okay, no arguments *twice*, same as .doit.().() (unspace form)
 

しかしながら、あなたは、コロンを付加することによって、上記の名指されたフォームの何でもリスト演算子に変えることができる:

.doit: 1,2,3        # okay, three arguments
.doit(1): 2,3       # okay, one argument plus list
.doit (): 1,2,3     # ILLEGAL (two terms in a row)
 

特に、これは我々が「標準の」引数のほかに最終のクロージャをパスすることを可能にする:

.doit: { $^a <=> $^b }              # okay
.doit(): { $^a <=> $^b }            # okay
.doit(1,2,3): { $^a <=> $^b }       # okay
 

通常スペースがコロンの後に前の名前を拡張する1対からすると当然起きることのあいまいさを排除するように要求される。 しかしながら、名前が拡張されないかもしれないで:{} 表記法を対にしろ、そうすればそのためにそれは、もしメソッドへの最初の引数がクロージャであるなら、コロンの後にスペースを落とすことを許される。 従って、上の(人たち・もの)の何でもコロンの後にスペースなしで書かれるかもしれない:

.doit:{ $^a <=> $^b }              # okay
.doit():{ $^a <=> $^b }            # okay
.doit(1,2,3):{ $^a <=> $^b }       # okay
 

そこにスペースがあるかのように、これらは解析される、それで、もしクロージャがコンマによって後に続かれるなら、引数リストは継続するかもしれない。

あいまい性の場合に間接的なオブジェクト表記法とドット形式の間に、最も近くのことは勝つ:

dothis $obj.dothat: 1,2,3
 

手段

dothis ($obj.dothat(1,2,3))
 

そしてあなたは言わなくちゃならない

dothis ($obj.dothat): 1,2,3
 

あるいは

$obj.dothat.dothis: 1,2,3
 

もしあなたが他のことを意味するなら。

同じくもしあるとしたらリストの項がそのままのクロージャあるいは pointy sub であることに注意を払え、カール状のクロージャの権利がコンマあるいはコロンによってすぐに後に続かれない限り、それはそのリストの最終の引数であると見なされるだろう。 特に、呼び出しがするメソッド * * ではなくがリストを拡張する、それであなたは言うことができる:

@list.grep: { $_ % 2 }.map: { $_ - 1 }.say
 

そしてそれは同等であると思われるだろうそうすること

@list.grep({ $_ % 2 }).map({ $_ - 1 }).say
 

コロンからこの場合スペースを必要としない、そしてそれはとにかくそこ(に・で)少し奇妙に見える、さらに多くがメソッドの1つの波状レース飾りに左手にそれらのように項に置く正しい外見が呼び出す上にメソッドを呼び出しにするスペースを除くことはいっそう明確であるかもしれない:

@list.grep:{ $_ % 2 }.map:{ $_ - 1 }.say
 

左辺値メソッド

メソッド(そして sub)が左辺値として宣言されるかもしれないでis rw.  権限:が引数のないを使うrw あなたが変数を使うことができるどこででもメソッドtemp そしてlet 文。 (実際、あなたは使うことができるrw 変更に実際の値を識別するために、引数がそれ以外の何ものでもなく使われるのと同じぐらい長い変数としての引数と一緒のメソッド、そしてさもなければ右辺値と左辺値使用の間に異なる奇妙な副作用を持つな。 しかしながら、引数として新しい値を期待する先駆者メソッドが行儀が良いカテゴリーに分類されない。)

スカラーコンテナ間接参照

変更可能なスカラーの上のメソッド呼び出しが常にオブジェクトに含まれる項目、スカラー(必要に応じてオートボクシング値型)、に行く:

$result = $object.doit();
$length = "mystring".codes;
 

メソッドがスカラーでない変数の上にただ呼び出しを呼び出すArrayHash あるいはCode 変数にバインドされたオブジェクト:

$elems = @array.elems;
@keys  = %hash.keys;
$sig   = &sub.signature;
 

接頭辞を使えVAR スカラー変数の上のマクロがその基礎となることに達するScalar オブジェクト:

if VAR($scalar).readonly {...}
 

VAR 非スカラ変数と値に無操作命令だ:

VAR(1);     # 1
VAR(@x);    # @x
 

同じく文通することがあるpostfix:<.VAR> それがメソッドであるかのように、使われることができるマクロ:

if $scalar.VAR.readonly {...}
 

(けれどもそれがマクロだから、VAR 実数メソッドとしてディスパッチされたではない。 ディスパッチに実数に.VAR メソッド、間接を使え$obj."VAR" できろ。)

あなたは適切なシンボルテーブルを通して同じくコンテナをほのめかすことができる:

if MY::<$scalar>.readonly {...}
 

クラスメソッド

他の OO 言語があなたにあるいはインスタンスに呼び出しを必要とするか、あるいは積極的に禁止しない「クラス」メソッドを宣言する能力を与える。 Perl 6 はあなたに選択を与える。 もしあなたたちが「クラス」メソッドいつとして普通のメソッド、それが関数をホールに入れると宣言する、あなたがそれに型オブジェクトをパスするならそんなものけれども「Dog」確定、プロトタイプオブジェクト、が、メソッドグループが何にもアクセスしようとしない限り、どのように現在のインスタンスで未定義の情報であるかにかかわらず.

代わる代わる、あなたはいっそう伝統的な「クラス」メソッドとしてメソッドを現在のメタクラスインスタンス、 singleton オブジェクトがあなたのパッケージを知っている、そして容器が関数を知っている(とき・から・につれて・ように)結び付けることができる:

our $count;
method ^count { return $count }
 

このようなメタクラスメソッドが常に委任先であるHOW メソッドが好むのとちょうど同じようにオブジェクト.does それがこれを呼び出すことが可能であるように、存在するDog.count あるいは$dog.count.  しかしながら、実践がおそらくのようなクラスメソッドを呼び出すはずであるベストDog.^count あるいは$dog.^count ネームスペースが普通のメソッド、そしてそれでそれからあなたのクラスを分離する、メソッドがサブクラスで偶然に普通のメソッドによってオーバーライドされることができないことはそれ自身のものであることを明確にするために - あなたがその可能性を考慮に入れることを望まないと推測すること。

Submethods

Submethods はイニシャライザのような、サブクラスによって継承されるべきじゃない infrastructural メソッドを宣言することに対してである:

submethod BUILD ($arg) {
    $.attr = $arg;
}
 

キーワードを別として、サブメソッド宣言と呼び出し構文はメソッド構文とまったく同じだ。 あなたはクラス階層以内に同一名のメソッドと submethods を混ぜてもよい、しかしただメソッドだけが継承としての導出クラスに見える。 メソッドであるときだけ、サブメソッドが呼び出される、呼び出しが現在のクラスに直接ディスパッチされる。

推測:それが定義するコンパイル時警告であるスペリングエラーのために何でのサブメソッドも捕えるために若干のベースクラスから対応するメソッド名を相続しないクラス。 もっと重要なことに、これは Liskov substitutability を保護するのに役立つだろう。 (けれどもそれほど標準的なメモMu クラスがすでにデフォルトを供給するBUILD そしてnew.)

属性

属性が、ハッシュでではなく、不透明なデータ型で記憶される。 クラスさえどのようにか気にするために、それらを持っていない、それらから、記憶される普通の変数とほとんど同じように宣言される. 代わりにmy使用has

class Dog is Mammal {
    has $.name = "fido";
    has $.tail is rw;
    has @.legs;
    has $!brain;
    ...
}
 

(クラスが終わりの括弧の前にその名前の明示的なメソッドを宣言しないなら)、公共の属性が同一名のアクセス機構メソッドの自動的な産出を示して、「ドット」の第二のシギルを持っている。 私的な属性が感嘆を公共のアクセス機構が生み出されないことを示すために使う。

    has $!brain;
 

変数が常にあたかもその人と一緒に感嘆、しかし多くを持っているプライベートの「真の名前」our 変数は、あなたはによって私的な変数にレキシカルにスコープ宣言されたエイリアスを宣言してもよい、次のように言って:

    has $brain;     # also declares $!brain;
 

と同じように! アクセス機構ではなく、宣言が生み出される。

そして何も後に、あなたが変数のプライバシーを強調するか、あるいは無視することを望む(とき・から・につれて・ように)、同じブロックの中の変数がそうするかもしれないプライベートへの参照が感嘆を使うか、あるいは除く。 区画の外(に・で)、あなたは使わなくちゃならない! できろ。 あなたが一緒に宣言するもし! できろ、あなたはどこでも首尾一貫してその形式を使わなくちゃならない。 あなたが一緒に宣言するもし. できろ、あなたは同じくプライベートをつかまえる! 実際の記憶位置とあなたの事実上でない名前がいずれかを使うかもしれない(とき・から・につれて・ように)、できろ! あるいは. たとえクラスが再開されるとしても、クラスの中でどこでもできろ。 クラスの外(に・で)あなたは大衆を使わなくちゃならない. できるか、あるいは(私的なメソッド呼び出しである、しかし信頼できるクラスだけのためであり得る)メソッド呼び出しに頼る。

公共の属性のために、若干のトレイトがアクセス機構メソッドにコピーされる。 rw トレイトが生み出されたアクセス機構を宣言されさせるrwそれを1つの左辺値メソッドにする。 デフォルトは読み取り専用アクセス機構だ。

あなたがクラスを宣言するもしrwそれからクラスが属性デフォルトであるすべてrwCとほとんど同じように、構造体。

あなたはあなた自身のアクセス機構に何あるいは自動的に生み出されたもののすべてでもオーバーライドするよう書くかもしれない。

属性変数はインスタンスメソッドの中で直接属性値に言及するために使われるかもしれない。 インスタンスメソッドの外(に・で)、オブジェクトが指定されなければならないから、属性への唯一のアクセスはアクセス機構を通してだ。 ドットフォームが常に事実上のアクセス機構呼び出しを暗示するから、属性変数のドットフォームは導出クラスで使われるかもしれない。 場所と感嘆が組織する宣言が同じく対応する私的なエクスクラメーション記憶域だと宣言するすべてのドットが、導出クラスでではなく、実クラスでだけ使われるかもしれない。 内部記憶域の場所までの参照として$!foo 一般に submethods に制限されるべきだ。 メソッドがくっつくべきである Ordinary $.foo できろ。

実際、使用 submethods の中での$.foo として利用可能な属性の上にできろ$!foo (それがである、このクラスによって直接宣言される)非合法であって、そして(隠されるかもしれない)緊急のコンパイル時警告を作り出す. サブメソッドの中で$.foo ただ親クラスのオブジェクトの部分だけが中に入っていることを保証されるから、形式がただ親クラスから属性で使われるかもしれない一貫した公式(からBUILDALL 呼び出しは親クラスのだBUILD 最初に定常課程). もしあなたが、宣言することによって、これを回避しようと試みるならBUILD メソッドとしてサブメソッドよりむしろ、それは同じく緊急の(しかし suppressibleの)コンパイル時警告としてマークされるだろう。 (inheritable を定義することは可能だBUILD もしあなたが現在のクラスのすべてのメタデータへのアクセスを持っている、しかしそれが容易じゃなく、そして、ただあなたが変わるからといって、それが確かに偶然起きないならルーチンsubmethod そうするためにmethod.)

から$.foo@.foo%.foo&.foo ただ速記であrnoself.foo 異なったコンテキストで、クラスは属性としてそれらの何も申告する必要がない - method foo 宣言が同じぐらいよく働くことができる。

標準のメソッド呼び出しフォームと同じように、ただ dotless 括弧だけが引数を含んでいるかもしれない。 もしあなたが使うなら.() メソッドの後の余分のレベルの間接参照が呼び出すそれが行なうであろう形式:

self.foo(1,2,3);    # a regular method call
self.foo.(1,2,3);   # self.foo().(1,2,3), call .() on closure returned by .foo
$.foo(1,2,3);       # calls self.foo under $ context
$.foo.(1,2,3);      # $.foo().(1,2,3), call .() on closure returned by .foo
&.foo(1,2,3);       # calls self.foo under & context
&.foo.(1,2,3);      # &.foo().(1,2,3), call .() on closure returned by .foo
 

属性デフォルト値

属性宣言への擬似割り当てがデフォルト値を指定する。 右手の値は暗黙のクロージャとして扱われて、そしてオブジェクト構築時間に評価される、それは、クラスが構成されているときではなく、オブジェクトが作成されているとき、だ。 コンパイルあるいは合成時間に計算された値に言及するために、あなたはあるいは一時的なあるいは時間的なある種のブロックを使うことができる:

has $.r = rand;     # each object gets different random value

constant $random = rand;
has $.r = $random;  # every object gets same value

has $.r = BEGIN { rand };
has $.r = INIT { rand };
has $.r = ENTER { rand };
has $.r = FIRST { rand };
has $.r = constant $myrand = rand;
 

それがいつにおいて呼び出されるかBUILD 時間、暗黙のクロージャのトピックは初期化される属性だろう、他方「self」が初期化されているオブジェクト全体に言及する。 クロージャは指定期間の末と呼び出されるだろうBUILD ただもしだけではないがさもなければシグネチャーあるいは体で初期化した属性BUILD.  クロージャは、それほど、実際に匿名のメソッドの主要部を定義するself (すべての親属性を含めて)やがてのそのポイントによって作成されるどんな属性ででも視聴可能だ。 イニシャライザはクラスの中で宣言について順に動かされる、それで所定の初期化演算子が先に起こることで属性確定に言及するかもしれないhas 宣言。

クラス属性

属性が同様一緒に宣言されるクラスmy あるいはour.  唯一の相違から普通my あるいはour 変数、第二のシギルによれば:アクセス機構が生み出されるということだ

our $.count;        # generates a public read-only .count accessor
our %!cache is rw;  # generates no public accessor
my  $.count;        # generates a public read-only .count accessor
my  %!cache is rw;  # generates no public accessor
 

構築と Initialization

すべてのクラスはデフォルトを相続するnew コンストラクタからMu.  それは同一名の属性を初期化する名指されたパラメータであるためにすべての引数を期待する。 あなたはあなた自身のものを書いてもよいnew デフォルトをオーバーライドするか、あるいは何ででもコンストラクタにあなたが好きである他の名前を書くために。 Perl 5 に、コンストラクタが何もである(とき・から・につれて・ように)それが呼び出すルーチンbless.  Perl 5 に、あなたが、パスして、クラスオブジェクト(どんなオブジェクトでも使用されるかもしれないけれどもクラスオブジェクト)にメソッドとしてそれを呼び出すと異なり最初の引数としての候補者。 例えば Perl 5 のようにハッシュを祝福するために:

$object = $class.bless({k1 => $v1, k2 => $v2, ...});
 

しかしながら、祝福するべき候補者を作り出す標準の方法が呼び出すことによってだCREATE (デフォルトによってのどちらが不透明なオブジェクトを引き起こすか):

$object = $class.bless($class.CREATE(), k1 => $v1, k2 => $v2, ...)
$object = $class.bless($class.CREATE(), :k1($v1), :k2($v2), ...)  # same
 

代わりに、あなたはパスすることができるWhatever そしてそうしたbless あなたのために CREATE を呼び出せ。

$object = $class.bless(*, k1 => $v1, k2 => $v2, ...)
 

候補者のほかに位置の引数、bless 同じく1人以上に autovivifying 型オブジェクトを表している位置の引数を許す。 このようなオブジェクトはハッシュ添え字によって後に続かれた型名のように見える(下の「Autovivifying オブジェクト」参照)。 これらはスーパークラスを初期化するために使われる。

対象オブジェクトと型を autovivifying している何以外にでもオブジェクト、そうするためのすべての引数bless 位置じゃない引数と命名されなくちゃならない。 従って、注文製のコンストラクタの主目的は賛成で位置の引数を名指された引数に変えるはずだbless.bless メソッドがオブジェクトがそのクラスインボカントのために使われることを可能にする。 (あなたのコンストラクタはこれを許す必要がない)。 何ででも場合、プロトタイプとして使用されたオブジェクトではない。 使用.clone 代わりに.bless もしそれがあなたが意味することであるなら。

意味規則のbless

Any は引数をそうするべく指名したbless 自動的にパスする to the CREATE そしてBUILD 定常課程。 あなたが特別なオプションをパスすることを望むもしCREATE (代わりの表示のような)ルーチン、呼び出しCREATE あなた自身、そしてそれから結果として生じている候補をパスしろ.bless

my $candidate = $class.CREATE(:repr<P6opaque>);
$object = $class.bless($candidate, :k1($v1), :k2($v2))
 

組込みデフォルトのためにCREATE メソッド、P6opaque デフォルト代表だ。 他の可能性がそうだP6hashP5hashP5arrayPyDictCstructなど.

bless 関数が自動的に適切なすべてを呼び出すBUILD 呼び出すことによって定常課程BUILDALL 大部分によって得られたオーダーに最少によって得られ中にオブジェクトを初期化する現在のクラスのためのルーチン。 DESTROY そしてDESTROYALL ただ後ろ向きに、同じように働け。

デフォルトBUILD そしてBUILDALL 遺伝するからMuあなたが省略時動作を修正することを望む場合に限り、あなたが初期化ルーチンを書く必要があるように。 bless 関数が自動的にパスする、適切な引数は傾く to the BUILD その種々の親クラスについて。 もし親クラスの型がオブジェクトが祝福するためにパスした型、それ型について1(人・つ)に対応するなら、オブジェクトの引数リストは使われる。 さもなければ祝福するべき引数がそうであるすべては親クラスのにパスしたBUILD.  決勝戦のためにBUILD 現在のオブジェクト、すべて引数についてそうするためにbless パスする to the BUILDそれが何ででも特別扱いを必要とする型オブジェクトを配ることができるように。 (それは何にも対応しない型オブジェクトに親クラスをパスすることを可能にされる。)

class Dog is Animal {...}
my $pet = Dog.new( :name<Fido>, Animal{ :blood<warm>, :legs(4) } );
 

ここで我々は autovivifying を使っているAnimal 何か明示する型オブジェクトをそうするための引数Animal「sBUILD ルーチンが見えるべきである. (それは実際は autovivify ではなくするAnimal (の・もの・人)を別として作られること。)

あなたはあなた自身のものを書くことができるBUILD サブメソッドが初期化をコントロールする。 もしあなたが属性をパラメータと名付けるなら、その属性はそれほど、直接、初期化される

submethod BUILD ($!tail, $!legs) {}
 

匹敵するものはそうするはずだ

submethod BUILD ($tail is copy, $legs is copy) {
    $!tail := $tail;
    $!legs := $legs;
}
 

あなたがあなた自身のものを書くかどうかBUILD あるいはそうじゃない、指定期間の末BUILDデフォルト属性値がそうである何でも暗黙的にどんな属性の中にもそれをコピーするさもなければ初期化された. それほどデフォルト的に注意しろBUILD ただ公共の属性を初期化するだろう;あなたはあなた自身のものを書かなくちゃならないBUILD (同じぐらい上に)私的な属性をあなたの初期化 API の一部として提示するために。

クローニング

あなたは、属性の若干を変えて、オブジェクトをクローンすることができる:

$newdog = $olddog.clone(:trick<RollOver>);
 

突然変異しているメソッド

権限:がこのように場所内 mutator メソッドを呼び出す:

@array .= sort;
 

場所内 mutator の1つの有用な場所が周知の型の変数にコンストラクタを呼び出すはずだ:

my Dog $spot .= new(:tail<LONG>, :legs<SHORT>);
 

メソッドのセットを呼び出す

何のためにでもメソッド名、要請を扱うことができたある程度の数の対象メソッドがあるかもしれない:典型的に、遺伝するメソッドあるいは多変形。 標準的なファッションのメソッドへの普通の「ドット」演算子ディスパッチ。 同じく同一名を持ったある程度の数のメソッドを呼び出す「ドット」変形がある:

$object.meth(@args)   # calls one method or dies
$object.?meth(@args)  # calls method if there is one, otherwise Nil
$object.*meth(@args)  # calls all methods (0 or more, () if none)
$object.+meth(@args)  # calls all methods (1 or more, die if none)
 

曖昧性除去が必要とされるとき、メソッド名は引用されるかもしれない:

$object."+meth"(@args)
$object.'VAR'(@args)
 

普通の呼び出しと同じように、リテラルのメソッド名を供給している識別子は間接的にメソッド名を指定するために補間挿入されたクォートで置き換えられるかもしれない。 それは同じくそうであるための候補の正確なリストが見なしたことを明示するために配列で置き換えられるかもしれない:

my @candidates := $object.WALK(:name<foo>, :breadth, :omit($?CLASS));
$object.*@candidates(@args);
 

WALK メソッドがこれらの引数をとる:

:canonical      # canonical dispatch order
:ascendant      # most-derived first, like destruction order
:descendant     # least-derived first, like construction order
:preorder       # like Perl 5 dispatch
:breadth        # like multi dispatch

:super              # only immediate parent classes
:name<name>         # only classes containing named method declaration
:omit(Selector)     # only classes that don't match selector
:include(Selector)  # only classes that match selector
 

Any メソッドが特別な関数によってリストで次の対象メソッドに従うことができるcallsamecallwithnextsameそしてnextwith.  「同じ」変形は現在のメソッドにパスされてオリジナルの引数リストを再利用する、のに対して変形「で」新しい引数リストが候補者の残りに代用されることを可能にする. 変形が、「次の」(人たち・もの)である間に変形が戻らない、しかしただ候補者リストの残りに従うのに対して、現在のメソッドに次の処理のために候補者とリターンそれら値の残りに急送する「呼び出し」:

callsame;           # call with the original arguments (return here)
callwith();         # call with no arguments (return here)
callwith(1,2,3);    # call with a new set of arguments (return here)
nextsame;           # redispatch with the original arguments (no return)
nextwith();         # redispatch with no arguments (no return)
nextwith(1,2,3);    # redispatch with a new set of arguments (no return)
 

ディスパッチが使うことに対して. そして.?帰りの値がであるCapture 延期することなしで最初のメソッド完了によって返される。 (このような帰りの値は実際失敗であるかもしれない、しかしそれは配車係の見地からまだ完了呼として扱われる。) 同じく帰りの値の.* そして.+ リストであrnoCaptures 次のメソッドに従わないで完成に走ったそれらのメソッドによって返す.

現在の呼び出しが最終の候補だと見なされるように、候補者リストを削減することは同じく可能だ。 (これは暗黙のうちにすでに一つの成功した呼び出しを必要とするディスパッチ変形のケースだ。) 多数の呼び出し変形のために、lastcall に離れてスローするべき配車係に候補者リストの残り、次の復帰メソッドが産み出すであろう流れから決勝戦をもたらすだろうCapture 返送されたリストで。 (もしあなたがすでに候補者リストの最後の呼び出しの上にいたなら、候補者が離れてスローされない、ただリストだけ。 あなたが、終端で動くことによって、偶然に間違ったリストをスローすることができないように、候補者からリストは最後の呼び出しの後まで配車係によって離れて通常スローされない。)

一度に1以上人以内の候補者にリストを急送していることが可能だから、これらの制御流れ呼び出しはダイナミックに一番奥のディスパッチャーにだけ適用されるために定義される。 例えば、あなたが一つのディスパッチを持っているもしproto 上にそれから倍数の中にディスパッチを呼び出すメソッドmulti クラスの中のメソッド、nextsame 人たちの1人以内にmultisが次のベストのところに行くだろうmulti オリジナルの一つのディスパッチでの次のメソッド候補者ではなく、クラスの中のメソッド。 ディスパッチループがダイナミックにスコープ宣言されるから;「ポップ」の望まれない対象をあなたがそうすることができる最も外側のリストに持って行く良くない限界が使ってリストするこのではないlastcall

lastcall; nextsame;  # call next in grandparent dispatcher loop
 

[推測:もし必要なら、lastcall 我々が我々のコンテキストについて確かじゃない場合に備えて、我々が我々が離れてどのディスパッチループの種類をスローしていると思うか明示するために引数あるいはインボカントを持っていることができた。 我々が使うから、この混乱は生ずることができたnextsame 少なくとも3つの異なった方法で意味規則:一つのディスパッチ、多数のディスパッチとルーチン包み紙ディスパッチ。]

平行したディスパッチ

メソッド呼び出しフォームの Any は、メソッド呼び出しを後置として扱うことによって、超演算子に変えられるかもしれない:

@object».meth(@args)   # calls one method on each
@object».?meth(@args)  # calls method if there is one on each
@object».*meth(@args)  # calls all methods (0 or more) on each
@object».+meth(@args)  # calls all methods (1 or more) on each
@object».=meth(@args)  # calls mutator method on each
@object»!meth(@args)   # calls private method on each
 

値がとして要素の正確に同数でリストである帰り@object.  おのおののそのような帰りの値がそうだParcel あるいはListParcel 非超「ドット」の変形のために上に指定されるように。

超演算子が、それほど、ジャンクションをスカラー値として扱う、次のように言って:

$junction».meth(@args);
 

ただ同種のものだ:

$junction.meth(@args);
 

メソッドの他のフォームと同じように呼び出し、上の「メス」は間接参照の種々のフォームをするために引用された文字列あるいは変数で置き換えられるかもしれない。

それに注意しろ、超演算子、メソッドが評価されるかもしれない何とでも同じように、(メソッド結果が常に invocants のリストと同じオーダーで返されるけれども)、何でも命令する。 もしあなたが I/O のような、順序づけられた副作用に関して何かをすることを望むなら、明示的なループを使え。

Multisubs と Multimethods

サブルーチンあるいはメソッドの「ロングネーム」はそのインボカント引数の型シグネチャーを含む。 「短い名前」はそうしない。

multi 宣言

あなたが置いたもしmulti 何の前(に・で)でも sub 宣言、それは多数のロングネームが、それらのすべてが宣言されるなら、短い名前を共有することを可能にするmultiあるいはそこ(に・で)一人の修道院次長だあるいは外のproto すべての印がない sub をデフォルトにそうさせる同じファイルで多そのレキシカルスコープで. もしではないが一緒に跡がついた sub multi そしてそれはそうじゃない通り過ぎてその同じファイルの中で支配するproto 同じ短い名前について、それはユニークであると見なされる、唯一の sub 。 (輸入するproto このような支配している宣言として関数を缶詰めにしろ。)

メソッド宣言、のためにprotomultiそしてonly 宣言が同様にしかし同じくではなく働く。 明示的な宣言は、統治と候補セットについて継承の木としての収益のその計算以外、同じを働かせるよりむしろ語彙の有効範囲規則として. 他の相違は既定の事実の proto メソッドがショートするということである仮定するべき強制的なすべて印がないメソッド宣言に名前をつける多サブクラスがどのファイルそれらかにかかわらず、明示的にオーバーライドされないなら、宣言されるすべてでとしてonly method.

only 宣言

only sub (あるいはメソッド)がそれの外のあるいはそれの前に申告される何かと共有しない。 ただ1つのそのような sub (あるいはメソッド)だけが所定のネームスペース(レキシカルスコープあるいはクラス)に生息することができる、そしてそれは同じ短い名前のどんな外の sub (あるいはさらに少なく得られたメソッド)をでも隠す。 それは賛成で非合法であるmulti あるいはproto 同じ範囲を共有するべき宣言only 同じ短い名前の宣言。

それらから異なったファイル、デフォルトから来いproto それほど、明示的に読み込まれないなら、設置スコープから Perl によって提供された宣言が自動的にデフォルトをユーザーのスコープにセットしないsub たまたま環境と同じであるそこの宣言proto そうである見なすonly 明示的に記録されていないなら、multi.  (これは我々が新しく付け加えることを可能にするproto ユーザーの古いコードを解かないで環境の宣言。) このような明示がないときにはsub しかしながら、宣言proto 一番奥の(人たち・もの)から外のレキシカルスコープがその短い名前にどんな呼び出しの分析ででもコンパイラによって使われる。 (ただリストだけから演算子はポストによって宣言されたかもしれない、コンパイラが非リスト演算の演算子を見るとすぐに、それは設定のを適用することが自由だproto 何からでもユーザー定義のonly それの機種が必然的に申告されるか、あるいはユーザーのファイル早くに、あるいはまったくではなく輸入されなくちゃならない。)

proto 宣言

Aproto 常に何の周りの配車係としての関数もmultisがそれの後に同じ範囲で、もっと特定すると、それが異なった候補者リストを持っているそれぞれのスコープで新たに例示されなくちゃならないディスパッチャーの一般的なプロトタイプだと宣言した。 (これはロールからクラスまでしゃれを言っている型とほとんど同じようにうまくいく。 あるいはあなたはこの配車係を候補者リストが適切であるという状態で、スコープへの proto のコードをカリー化することであると考えることができる。) 論議のために、我々に宣言詞同等物があると言わせろonly それはその代わりにつづられるdispatch.  一般にユーザーが決して書かないdispatch sub (それは許されさえしていないかもしれない);dispatch 常に支配することからインスタンスを作られるproto.  A new dispatch 1つ、それを必要とする範囲が、その親スコープ(あるいは、多数の継承のケースの、スコープ)より多宣言の異なったセットを見ることができるどんな範囲ででも、そうである sub あるいはメソッドが何ででも自動的に生み出される。

いっそう正確に、与えられた何もの間proto そして呼び出しのポイント、通り過ぎて下方へ支配された2セットの:ルーチンのセットの交差点である候補1セットのルーチン(関数あるいはメソッド)があるproto そして上方に呼び出しのポイントから目に見える定常課程のセット。 それは再利用に許されるdispatch 親スコープについてもしそれが同じ候補者をもたらすであろう場合に限り、そしてその場合には必ず、現在の範囲(呼び出しのポイントでのスコープ)で傾け。

それ以来dispatch ほとんど同一であるそうすることonly言う&foo 常に一番奥の visible に言及するdispatch あるいはonly sub 、 never から a proto あるいはmulti.  同じく、$obj.can('foo') 大部分によって得られた(人たち・もの)を返すだろうdispatch あるいはonly メソッド。

proto シグネチャー

そのスコープの中で、シグネチャーのproto 範囲がその情報に基づいてポジショナルパラメータにそれらの引数を再調整することをあえてすることができるという点で、何でもそれに名指された引数と一緒の短い名前を呼び出すように、同じく仮定されたオーダーとポジショナルパラメータのネーミングを確定する。 (認められない名前が引数という名前のままでいる。) Any の他の型情報、あるいは付随されたトレイトproto 同じく、それほど、そのスコープの中の定常課程に伝えられるかもしれないproto 定義が共通トレイトを要因から外すために使われることができる。 これは、宣言することによって、文法で文法的なカテゴリーを確証することに対して、特に有用であるproto token あるいはproto rule.  (Perl 6 の文法は例えばこれをする。)

multi 変数

権限:が複数を持っているmulti 同じ範囲とそれらでの同一名の変数がすべて同じ記憶域場所と型を共有する。 これらは1人によって宣言されるproto トップでの宣言、あなたがどちらのケースに去るかもしれないかmulti 同じ範囲で宣言の残りの上に暗示的だ。 あなたがあなたが同じ変数名(このようなコードがマクロによってあるいは例えばコード生成プログラムによって作り出されるかもしれない)の多重宣言を持っているであろうと思うとき、あなたはこれをするかもしれない、そしてあなたは再定義についてどんな可能な警告も隠すことを望む。

multi Routine

それと対照的に、multi ルーチンがどんなネームスペースででもロングネームのたった1つの例を持っていることができる、そしてそのインスタンスは同じロングネームでどんな外の(か、あるいはさらに少なく得られた)ルーチンでも隠す。 それは同じ短い名前じゃなくて異なったロングネームを持ったどんな定常課程でも隠す。 言い換えれば、multiそれらロングネームが異なり、そしてそれらショートネームが通り過ぎて隠れていないなら、同じ短い名前を持っているsがいくつかの異なったネームスペースから来ることができるonly あるいはproto 若干の中間の範囲の宣言。

Multisub 解決

あなたが特定の短い名前でルーチンを呼び出すとき、もし多数の目に見えるロングネームがあるなら、それらは候補者だと見なされたすべてだ。 それらがオーダーの中に解決しているによれば引数の実行時型がどれほど近くそれぞれの候補のパラメータの宣言型で上へマッチするか. タイがないなら、最も良い候補は呼び出される、その場合候補者がそうであるタイされた人たちは何でも使って追加のタイブレーク戦略を再びディスパッチした(下を見る)。 型がだと見なされるではなくぎこちなくないこの名目上のタイピングの目的で型であるために、名前をつけろ;その代わりにぎこちない型はその基底型プラス制約の中にほどかれる。 ただぎこちない型が基づいているベース型だけが(それがぎこちないという事実とともに)名目上の型マッチに関して見なされる。 すなわち、もしあなたがパラメータを持っているなら:

subset Odd of Int where { $_ % 2 }
proto foo {*}
multi foo (Odd $i) {...}
 

あなたがその代わりに言ったかのように、それは扱われる:

multi foo (Int $i where { $_ % 2 }) {...}
 

ぎこちない型がそうである Any で対応する拘束されない型より狭い「エプシロン」であるベース型を持つために見なした。 コンパイル時トポロジカルソートは少なくとも1つの制約の存在を考慮に入れる、しかしおよそ数あるいは何もの性質の何も追加の制約を考慮に入れる。 我々が Int について「何かが Int 、それから Int のバージョンを制限したように」と思うかどうかが名目上は Int より常にもっと厳しい。 (Int」 Perl 6 構文ではなく、メタ表記法だ。)

候補者がいるオーダーを考慮して参加しているそれぞれのパラメータの不寛容の上にそれが今度は依存するそれぞれの候補者のロングネームの「型不寛容」に基づいたトポロジカルソートによって定義される。 同一の型がタイされていたと見なされる。 その型が類似じゃないパラメータが同じくタイされていたと見なされる。 もしそのパラメータの少なくとも1つがもっと狭く、そしてすべてそのパラメータの残りが同様もっと狭い、あるいはタイされるなら、候補がもう1人の候補者より狭いと見なされる。 同じく、もしシグネチャーが何も持っているなら、ロングネーム、シグネチャー全体に参加しないことがそうである追加の必須パラメータが余分のパラメータなしでエプシロンの何よりももっときついシグネチャーを見なした。 本質的に、ユーザーがキャプチャパラメータが引数の残りをバインドすると宣言したかのように、残っている引数は longname に加えられる、そしてそのキャプチャパラメータはそれが追加の必須パラメータに成功裏にバインドしなくちゃならない制約を持っている。 所定のランクの中のすべてのそのようなシグネチャーが同等で、そして下にタイブレークBの適用を受けると見なされる。

これはすべての候補の半順序を定義する。 トポロジカルソートが半順序で堂々巡りを検出する、円でのすべての候補者がそうであるかどうかがタイされて見なした。 警告が表示されるであろうでCHECK これが発見される、そしてタイを破ることができた適切なタイブレークがないかどうか時間を測れ。

候補者 Tiebreaking

絶望の増加するオーダーで、3つの tiebreaking 様式がある:

A) inner or derived scope
B) run-time constraint processing
C) use of a candidate marked with "is default"
 

タイブレークAが外か、あるいはそれほど派生されないスコープでただ内面的か、あるいはさらに多くによって得られたスコープで候補より候補の方が好きだ。 候補のために同じ範囲で、我々はタイブレークBに進む。

何でもないときには拘束知識、がタイブレークAですぐにそうするためのフェイルオーバをタイする、Cによってもしそうでなければ解決されたタイブレークC、それらがコンパイル時間にあいまいなディスパッチについて警告する。

もし制約を持っている候補、それが当然起きるタイされた何かがあるなら、上記の我々の定義でそれらのすべてがそうであることはぎこちないために見なした。 longname パラメータのあるところで制約、あるいは余分の必要とされる引数の暗黙の制約で、タイブレークBが適用される。 ユーザーが正確にそれぞれの候補者がなぜそれが持っている余分の制約を持っているか知っていると想定される限りにおいて、名目上はタイされる、しかし制約を持っている候補者が完全に異なった状況であると見なされる。 それで、ぎこちないシグネチャーがずっとスイッチのようにユーザーによって定義されると見なされる。 候補者が簡単に呼び出されるほどタイブレークBのためにオーダーでそれらが宣言された、そして成功裏にバインドする(そして nextsame あるいは nextwith を呼び出さないで完了する)最初のが他がタイした勝利者とすべてだと見なされる、候補が無視される。 もしぎこちない候補者が落第点を付ける、我々がスローするすべてが制限された変形のランクの外にそしてどちらが、次のもっと厳しい階級に、進んでも余分の引数なしで自然な変形から成り立つなら。

タイブレークCが一緒に表わされた使われた:唯一の候補である、制約(タイブレークB)によって、決定されないランクのためにdefault トレイトは熟考された、そして最も良いマッチしているデフォルトのルーチンが使われるということだ。 もしデフォルトルーチンがないなら、あるいはもしデフォルトの2かそれ以上が、最も良く、ディスパッチ失敗のためにタイされるなら。

パラメータ制約除外

通常マルチ sub のすべてのパラメータはディスパッチに関して見なされる。 整数レンジ演算子のためにそのロングネームで2つのパラメータでここに宣言がある:

multi sub infix:<..>(Int $min, Int $max) {...}
 

時々あなたはロングネームの一部として勘定に入れられないパラメータを持つことを望む。 例えば、もしあなたがあなたのレンジ演算子に任意の「ステップ」パラメータを許すけれども見なさないことを望む、それがマルチディスパッチのために、それからコンマの代わりの二重のセミコロンをそれの前に置いたなら:

multi sub infix:<..>(Int $min, Int $max;; Int $by = 1) {...}
 

セミコロンが、もしあるとしたら、完全なロングネームを決定するダブルmulti.  (それがないので、最後の人が引数を宣言した後、しかし何でもシグネチャーを返す前に、二重のセミコロンが想定される。) ルーチンへの呼び出しがまだ次の引数と互換性がなくてはならないとは、注意しろ。

それに注意する$by 必須パラメータじゃなくて、それほどタイブレークBを許す種類の制約を課さない。 もしデフォルトが除かれたなら、それは必須パラメータであって、そしてタイブレークを普通の名指されたパラメータが参加しないタイブレーク B. Likewise に合わせるだろう、しかしあなたは名指されたバインディングに基づいて名指されたパラメータに効果的にスイッチを作るために必要とされるという記録を残すことができる:

multi foo (Int $a;; :$x!) {...}     # constrained
multi foo (Int $a;; :$y!) {...}     # constrained
multi foo (Int $a;; :$z!) {...}     # constrained

multi foo (Int $a;; *%_) {...}      # unconstrained
 

最初の3は制限されたランクとしてタイブレークBの下でディスパッチされる。 もしそれらの少しがマッチすることができないなら、最終の(の・もの・人)はそれ以来、自然なランクとして、ディスパッチされる*%_ ではないが必須パラメータを見なした。

ぎこちない型候補者

同じく、ぎこちない型が無制約の前にソートする:

multi bar (Even $a) {...}   # constrained
multi bar (Odd $a) {...}    # constrained

multi bar (Int $a) {...}    # unconstrained
 

そして同じくサブセット型として使用された値が最初にソートして、そしてファーストからマッチへの基礎の上にディスパッチされる:

multi baz (0) {...}         # constrained
multi baz (1) {...}         # constrained

multi baz (Int $x) {...}    # unconstrained
 

もしぎこちない候補者の若干が他のモジュールからの輸入を手に入れるなら、それらがの目的のため輸入のポイントにおいて宣言されるべき見なされたすべてである tiebreaking する;次の tiebreaking が中古のモジュールの中でオリジナルの命令によって提供される.

[推測:しかしながら、既定の事実multi その若干が完全なロングネームより短い多数のロングネームを広告するかもしれない。 それぞれがロングネームを宣伝した後、これはセミコロンを置く(もし存在しているなら、コンマを置き換える)ことによって、される。 セミコロンが2人の候補者をリストに挿入する効果を持っている。 セミコロンがコンマであるかのように、それらの1つがまったく同じ型で差し込まれる。 セミコロンの後のすべての型が型の(こと・もの)であるかのように、他が差し込まれるAnyそれはリストでもっと狭い実際の候補より遅れてそれを置く。 これはただそのソート順を決定する;もし、候補者リストのすべてのより以前の項目を拒絶した後で、配車係がそれに到着するなら、候補者はその実数型シグネチャーを使う。 もし遅れている候補のそのセットが同じく結びつきを含んでいるなら、追加のセミコロンが結びつきのその部分リストの中の同じ影響を持っている。 注意しろ、しかしながら、もしそれの後の型がすべてであるなら、そのセミコロンは無操作命令だAny.  (制限する訴訟として、共通とほとんど同じようにすべてのパラメータがディスパッチ意味規則を作成したあとのセミコロンに Lisp を発する。 そして、ただ最初の引数だけが普通の一つのディスパッチのメソッドとほとんど同じようであった後、セミコロンを記入する。) 注意しろ:この一つのセミコロンの構文はただ我々がそれの意味規則を理解するまで、そしていっそう重要なことに遠慮がちであると見なされるはずだ、(それが何でも持っているか否かにかかわらず、正当な使用場合である)それの pragamatics 。 その時までただ二重のセミコロンの形式だけが標準語で実装されるだろう。]

Amethod あるいはsubmethod 通常サブルーチン - ディスパッチプロセスに参加しない。 しかしながら、それらがもし前接続されるならそうさせられることができるでmy あるいはour 宣言詞。

多 Submethods など

普通の submethods がそうであるのとちょうど同じように、それら以外の多メソッドがインボカントに正確な型マッチに限定されるのとまったく同じように、多 submethods が機能する。

ただポジショナルパラメータの上に、名指されたパラメータの上に多数のディスパッチをサポートするために必要とされる Perl 6.0.0のではない。 どんなにそれほど何も的であるとしても、ディスパッチャが生じたことに注意を払えproto 周知の宣言されたポジショナルパラメータと呼び出しに名指された引数をマップするだろうmulti 名指された引数よりむしろそれらの引数の positionals を持っている候補者。

多数のディスパッチの中で、nextsame 次の最も良いマッチ、あるいはタイの場合で次の最も良いデフォルトを試みるつもりだ。

sub キーワードがすぐに後でオプションであるprotomultiあるいはonly ただ、キーワードmethod キーワードではない。

Aproto 宣言が後で起こらないかもしれないmulti 同じ範囲の宣言。

メソッド呼び出し対サブルーチン呼び出し

呼び出し側は呼び出し構文までにメソッドを呼び出しあるいはサブルーチン呼び出しにするべきかどうかを示す。 フォームとメソッドへの間接的なオブジェクト書式デフォルトが呼び出す「ドット」。 他のすべての接頭辞がサブルーチン呼び出しにデフォルトを呼び出す。 これは同様に接頭辞単項演算子に当てはまる:

!$obj;  # same as $obj.prefix:<!>
 

呼び出しがそのインボカントのクラス階層から(多メソッドと submethods を含めて)ただメソッドだけだと見なして、そしてもしどれも見いだされないなら失敗するメソッド。 問題のオブジェクトはメソッド名の意味を解釈することの責任を持っている、それでもしオブジェクトが外国のオブジェクトであるなら、名前はその外国のランタイムだけ解釈されるだろう。

サブルーチン呼び出しが見なす、ただ(submethods を含めて)その名前の目に見えるサブルーチン。 オブジェクトはディスパッチでそれ自身発言権を持っていない;サブルーチンディスパッチャーは見なす、ただ引数が、名前とともに、巻き込んだ型。 従って外国のオブジェクトがパスした、からサブルーチンが、(外国の型が Perl 型、さもなければそれら失敗の中に強制されることができる限りにおいて)、 Perl 意味規則の後に続くことを強いられる。

同様サブルーチンからメソッドディスパッチまで、フェイルオーバがない、あるいはその逆だ。 しかしながら、あなたは使ってもよいis export それを同じく利用可能にするべきメソッド定義の上にmulti sub 。 間接的なオブジェクト構文と同じように、最初の引数はまだ常にインボカントだ、しかし輸出はあなたがコロンの代わりにインボカントの後にコンマを使うことか、あるいはインボカント以外の引数がないメソッドに関しては完全にコロンを除くことを可能にする。 多くの標準的なメソッド(そんなものけれどもIO::close そしてArray::push)自動的に輸出される to the CORE デフォルトによってのネームスペース。 他の輸出されたメソッドのために、あなたは見ないだろうmulti あなたじゃないなら sub 鮮明度use あなたのスコープで、それが読み込むであろうクラスproto (そして関連づけられたmulti sub)、レキシカルに、どちらの後にあなたは標準のサブルーチン呼び出し構文を使ってそれを呼び出すことができる.

明示的な型がないときにはメソッドのインボカント、輸出された(人たち・もの)にmulti sub の最初の引数は暗黙のうちにそれが定義されたか、あるいは、それほど例えば、構成されたクラスとマッチすることを強制されるmulti 機種のclose その最初の引数に型の(こと・もの)であるように要求するIO あるいはそのサブクラスの1つ。 もしインボカントが明示的にタイプされるなら、それは文通することの型報道を支配するだろうmulti「s最初の引数、それがクラスのインボカントよりいっそう特定か、あるいはいっそう一般的かどうかは当然そうだろう。 (けれどもそれもしそれがいっそう特定であることを知っていろ::?CLASSバインディングマルチディスパッチと同様、さもなければ正当な一つのディスパッチを拒絶するかもしれない。) 何でも、もしルーチン自身がより広い型を扱うことができないなら、場合、それはインボカントを一般化し過ぎるために善行をしない。 このような状況であなたはもっと狭い型に強制するべき包み紙を書かなくちゃならない。

信託

属性が、特定のクラス定義に、タイされる、それで、インボカントがその属性の「self」であるとき、メソッドがただ直接それが中で定義されるクラスの属性にアクセスすることができる。 しかしながら、もしその他のクラスがそれが多メソッドが定義されるクラスを信頼することを示したなら、それは異なったクラスから私的な属性アクセス機構を呼び出すかもしれない:

class MyClass {
    trusts YourClass;
    ...
}
 

トラストは本当にただそうする申請をするだけだMyClassその可能なサブクラスにじゃない。

そうするための後部を呼び出すための構文MyClass 存在する$obj!MyClass::meth().  どのオブジェクトが言及されているかについて、私的な属性アクセス機構が常に、決して配車係としてじゃなくて、直接訴えられて、決して何もないから質問することに注意を払え。 従って、個人的なアクセス機構表記法は積極的に単純な属性のためにインライン化されるかもしれない、そして、もう1つのオブジェクトの私的な属性にアクセスすることに対して、より単純な表記法が必要とされない。

代表団

委任があなたに何か他のオブジェクトのメソッドがあなた自身のものであるというふりをさせる。 随行団が通り過ぎて指定されて存在するhandles 共通での現在のオブジェクトと委任オブジェクトが持つであろう1つ以上のメソッド名を指定している引数と一緒のトレイト動詞:

has $tail handles 'wag';
 

メソッド名(しかし他の何も)がクラス構築時間、次のことにおいて知られていないから.wag メソッドがあなたのために自動的に生み出される:

method wag (|$args) { $!tail.wag(|$args) }
 

あなたは多数のメソッド名を指定することができる:

has $.legs handles <walk run lope shake lift>;
 

属性が通り過ぎてのような、メソッドをサポートしている型のオブジェクトに初期化されなかった限り、外のメソッドを呼び出すことは非合法だ:

has Tail $.tail handles 'wag' .= new(|%_);
 

そのパッティングに注意するTail 属性の上の型が必ずしもメソッドが常に委任先であることを意味しないTail クラス。 ディスパッチはまだ基礎を置かれる、逃げ回って - がオブジェクトの型の時間を測定する、宣言された(人たち・もの)ではなく型。

Any 他が引数についてそうするとは思いやり深いhandles そうであると見なされるメソッド名のためにセレクタにスマートマッチする. すべてのそのようなセレクターが使われるフェイルオーバのみを確立する、もしディスパッチが、それが何でもオーバーライドするために使われることができないように、失敗する標準のメソッドがオブジェクトの標準の先祖でのメソッドを確立する。 それであなたが言うことができる:

has $.fur is rw handles /^get_/;
 

もしあなたが言うなら

has $.fur is rw handles Groomable;
 

それからあなたはただそれらのメソッドだけを利用可能にするとしてGroomable ロールあるいはクラス。 すべてを委任して、使うことWhatever 照合回路:

has $the_real_me handles *;
 

それがただこのオブジェクトであるいはその親の何でもどこでもメソッド名への正確なマッチがないことを決心していた後になるまで、ワイルドカードマッチが評価される。 あなたが異なったオブジェクトへの多数のワイルドカード代表団を持っているとき、メソッド名の競合を持つことは可能だ。 ワイルドカードメソッドマッチが順に評価される、それで最も早く1人は勝つ。 (非ワイルドカードのメソッド競合がクラス作文時に捕えられることができる。) もしこのクラスのためのワイルドカードが何も見いださないなら、ワイルドカードが標準的なメソッド選択オーダーで先祖のクラスのそれぞれがないかチェックされる。

もし、あなたが通常文字列を指定するであろうところで、あなたが1対を置いたなら、二人が他のクラスでこのクラスでのメソッド名をメソッド名にマップする。 もしあなたがハッシュを置いたなら、それぞれのキー / 値のペアがこのようなマッピングとして扱われる。 このようなマッピングはワイルドカードだと見なされない。

has $.fur handles { :shakefur<shake>, :scratch<get_fleas> };
 

あなたは改名しているが、ペアと一緒じゃないワイルドカードをすることができる。 その代わりにそうするスマートマッチする置換で :

has $.fur handles (s/^furget_/get_/);
 

通常随行団はオブジェクトを持っていて属性に基づいている、しかしそれは同じくメソッドのリターン値に基づき得る:

method select_tail handles <wag hang> {...}
 

型とサブタイプ

Perl の型システムはロール、クラスとサブタイプから成り立つ。 あなたはこのようなサブタイプを宣言することができる:

my subset Str_not2b of Str where /^[isnt|arent|amnot|aint]$/;
 

あるいはこれ:

my Str subset Str_not2b where /^[isnt|arent|amnot|aint]$/;
 

このような匿名のサブタイプビジュアル:

Str where /^[isnt|arent|amnot|aint]$/;
 

Awhere 文節がいずれかの種類の未来のスマートマッチを暗示する:左手の型のまだ特定されていないオブジェクトは右手にセレクターとマッチするに違いない。 我々の例は乱暴にこのクロージャと等しい:

{ $_.does(Str) and $_ ~~ /^[isnt|arent|amnot|aint]$/; }
 

それ以外サブタイプがいつそれ自身を呼び出すべきか知っている。

サブタイプはサブクラスじゃない。 サブクラスが能力を加えるのに対して、サブタイプが制約を加える(capabilites を取り去る)。 サブタイプは主にスマートマッチを多数のディスパッチにこっそり持ち込む有用な方法だ。 ロールがあなたにクラスよりいっそう一般的な何かを指定することを許すのとちょうど同じ(ように・時に)、サブタイプがあなたがクラスよりいっそう特定の何かを指定することを可能にする。 サブタイプが我々が使う理由であるオリジナルの型が指定した値のサブセットを指定するsubset それのためのキーワード。

多数のディスパッチのためにパラメータ型を限定することに対して、サブタイプが主に意図的である間に、それらが同じくあなたに割り当てに前提条件を押し付けさせた。 もしあなたがサブタイプで何でもコンテナだと宣言する、 Perl が制約を何かと照らし合わせるであろうならあなたがコンテナにバインドするか、あるいは割り当てようとするかもしれない値。

subset Str_not2b of Str where /^[isnt|arent|amnot|aint]$/;
subset EvenNum   of Num where { $^n % 2 == 0 }

my Str_not2b $hamlet;
$hamlet = 'isnt';   # Okay because 'isnt' ~~ /^[isnt|arent|amnot|aint]$/
$hamlet = 'amnt';   # Bzzzzzzzt!   'amnt' !~~ /^[isnt|arent|amnot|aint]$/

my EvenNum $n;
$n = 2;             # Okay
$n = -2;            # Okay
$n = 0;             # Okay
$n = 3;             # Bzzzzzzzt
 

それは1つのサブタイプをもう1つに基礎づけるために正当だ;それはただ追加の制約を加える。 すなわち、それはサブセットのサブセットだ。

権限:がシグネチャーで匿名のサブタイプを使う:

sub check_even (Num where { $^n % 2 == 0 } $even) {...}
 

それはあなたが表に変数を得るために周りにそれになることができる少し扱いにくいが、標準の型によっての宣言ルールだ:

sub check_even ($even of Num where { $^n % 2 == 0 }) {...}
 

そしてただ便利さのために我々は同じくあなたにそれを書かせた:

sub check_even (Num $even where { $^n % 2 == 0 }) {...}
 

すべての型からシグネチャーパラメータの制約はとにかく一緒にただ andedだ。

ブロックマッチしているとき、リテラルの値に対していずれかの種類から外れている権限:休暇:

proto sub fib (Int $) {*}
multi sub fib (Int $n where 0|1) { return $n }
multi sub fib (Int $n) { return fib($n-1) + fib($n-2) }
 

実際、あなたは外に去ることができるwhere まったく宣言:

multi sub fib (0) { return 0 }
multi sub fib (1) { return 1 }
multi sub fib (Int $n) { return fib($n-1) + fib($n-2) }
 

サブタイプ制約が多数のディスパッチでタイブレークとして使用される:

use Rules::Common :profanity;

multi sub mesg ($mesg of Str where /<profanity>/ is copy) {
    $mesg ~~ s:g/<profanity>/[expletive deleted]/;
    print $MESG_LOG: $mesg;
}

multi sub mesg ($mesg of Str) {
    print $MESG_LOG: $mesg;
}
 

多ディスパッチのために、マッチしている制約を持っているロングネームが制約がない同等の(の・もの・人)より好まれる。 それで最初mesg 上に、もし制約がマッチする;さもなければ第2が好まれるなら、好まれる。

サブセット型を輸出して、すぐ前に輸出トレイトを置くことwhere

subset Positive of Int is export where * > 0;
 

抽象的対具体的な型

型という名前の何、型でも付加して通り過ぎて自動的にそれから生じるかもしれないある特定の他のサブセットのために適切な副詞のその名前:に

Int:_       Allow either defined or undefined Int values
Int:D       Allow only defined (concrete) Int values
Int:U       Allow only undefined (abstract or failure) Int values
Int:T       Allow Int only as a type object
 

すなわち、これらは何かが好むことを意味する:

Int:D       Int:_ where DEFINITE($_)
Int:U       Int:_ where not(DEFINITE($_))
Int:T       Int:U where none(Failure)
 

どこ(で・に)かDEFINITE 問題のオブジェクトが効力がある具体的な表示を持っているかどうか言うブールのマクロだ(下の内省参照)。

スタンダード Perl 6 に、Int 一般に、平均に仮定されるInt:_invocants 以外、デフォルトがあるところInt:D.  (デフォルトnew メソッドがそのインボカントが存在するプロトタイプを持っている:T その代わりに、型オブジェクトを許すことに、メソッドがすべて義務を怠るほどすべて新しい。)

これらのデフォルトは種々のプラグマによってレキシカルスコープの中で変えられるかもしれない。 特に、

use parameters :D;
 

非インボカントのパラメータをデフォルトにそうさせるだろう:D.  推測的に、

use variables :D;
 

変数宣言で使われた型のために同じことをするだろう。

あなたが使うかもしれないこのようなレキシカルスコープで:_ 標準的な振る舞いに戻るためにできろ。 特に、 invocants デフォルトから確定に、

use invocant :_;
 

invocants にまあ言わば定義された何もあるいは未定義のインボカントを許させるだろう。

多数の制約

[推測:このセクション全体は我々のポスト - 6.0.0指示に推測だと見なされる。 6.0.0でもしすべてが左手に一つの型より狭い「エプシロン」だと見なされるなら、我々は変数の前にただ一つの制約だけを許して、そして制約を公表するだろう。 左手の一つの制約は、しかしながら、0のような値あるいは名指されたサブセット型であるかもしれない。 型が一緒に前もって宣言されるかもしれないこのような名指されたサブセット独断的に複雑where 何でも型情報 inferrable を組み立てる;6.0.0のための、文節where 文節が無視されるだろう、そして型がただ名目上は生じると見なされるであろう宣言されたサブセットof 型が同じことで宣言に言及した。]

いっそう一般には、パラメータが制約のセットを持っていることができる、そして制約のセットはシグネチャーに同じぐらい見えるパラメータの正式の型を定義する。 (それがネイティブの型じゃない限り、1つの制約が実際の引数の記憶域型として恵まれていない。) すべての制約は型狭さで評価されている。 すなわち、これらは等しく狭い:

Foo Bar @x
Bar Foo @x
 

同じくシギルによって暗示された制約は公式の型の一部として扱われる。 シギルは実際は実際の上記のパラメータの型が何かである、それほど、コンテナの上の制約だ:

Positional[subset :: of Any where Foo & Bar }]
 

雑音where 条項は同じく公式の型の一部として扱われる。 Awhere もしそれが値の周知の有限集合を産み出すためにコンパイル時間にそれの左に型に適用されることができるなら、文節がスタティックであると見なされる。 例えば、サブセットは値についてセットされて列挙型型について批判だ。 従って

Day $d where 'Mon'..'Fri'
 

熟考された等価物はそうするはずだ

subset Weekday of Day where 'Mon'..'Fri';
Weekday $d
 

型が dynamic で言及されるwhere クラスが存在しない公式の型の一部が、型が概念を含む限りにおいて以外:「同じく原動力によって拘束されると見なすwhere 条項」、それは同等の型にわたってなしにエプシロンによってそれを狭めるwhere 条項。

Foo Bar @x              # type is Foo & Bar & Positional
Foo Bar @x where Baz    # slightly tighter than Foo Bar Positional
 

パラメータのための制約のセットはパラメータのために許可値についていずれかのセットを暗示するサブセット型を作る。 許容値のセットはコンパイル時間に determinable であるかもしれない、あるいはそうしないかもしれない。 セットが許可値について determinable にコンパイル時間に、我々がそれを呼び出すということであるとき静的なサブタイプ。

(要素の固定セットが理解可能であるという状態で、(もし知られていないなら)コンパイル時間にある)スタティックなサブタイプに確認する型制約が実行時損得勘定を伴うか、あるいはさもなければ、コンパイル時間に手に負えない型制約より狭いと見なされる。 0のようなすべての値あるいは「foo」が singleton 静的サブタイプだと見なされることに注意を払え。 Singleton 値がたとえサブタイプが問題の値を含むとしても多数の値で、サブタイプより狭いと見なされる。 これは、可算の型のために、型狭さが、列挙された値のセットの上に集合論をすることによって、定義されるからだ。

それで仮定すること:

my enum Day ['Sun','Mon','Tue','Wed','Thu','Fri','Sat'];
subset Weekday of Day where 'Mon' .. 'Fri'; # considered static
subset Today of Day where *.today;
 

我々は次の序列を持っている:

Parameter                   # Set of possible values
=========                   ========================
Int $n                      # Int

Int $n where Today          # Int plus dynamic where
Int $n where 1 <= * <= 5    # Int plus dynamic where

Day $n                      # 0..6

Day $n where Today          # 0..6 plus dynamic where

Day $n where 1 <= * <= 5    # 1..5
Int $n where Weekday        # 1..5
Day $n where Weekday        # 1..5
Weekday $n                  # 1..5

Tue                         # 2
 

中間で相違に注意しろ:

Int $n where 1 <= * <= 5    # Int plus dynamic where
Day $n where 1 <= * <= 5    # 1..5
 

最初where ただ比較の性質のためにではなくダイナミックであると見なされるからInt 有限で可算のではない。 我々Weekday それが上に基礎を置かれるから、型が親子関係を計算することができるサブセットが時間をコンパイルするDay 列挙型、そして従って用途にもかかわらず静的であると見なされるのwhere.  持っていた我々基礎を置くWeekday 上にInt それはダイナミックであると見なされただろう。 注意する、しかしながら、「anded」制約、何ででも列挙型型が、それほど、もっと緩い型を支配すること

Int Day $n where 1 <= * <= 5
 

それ以来、静的であると見なされるDay 列挙型であって、そして探索空間を減らす。

我々がほのめかそうとしている基本原則はこれだ:2つのパラメーターの型を比較することにおいて、不寛容は、制約、あるいは(それによって)それらの制約が指定されるメソッドの名前に関してではなく、可能な値のセットのサブセット関係によって決定される。 実際的な理由で、我々は我々のサブセット知識を制限する、からコンパイル時間に容易に知られていて、そして見なすことができるものは動的制約なしで可能な値の同じセットより狭いエプシロンである1つ以上の動的制約の存在を制限する。

最初の近似として6.0.0で、列挙型の下位グループはスタティックだ、そして他の下位グループはダイナミックだ。 我々は Perl の次のバージョンでこれを改善するかもしれない。

目録

目録は不変の値についてセットを表すためのシンボルのセットの使用を促進する型だ。 その最も明白な使用は(彼・それ)らの対応する値にそれらのシンボルの翻訳だ。 それぞれの列挙連合が型の(こと・もの)である列挙型として知られている不変の対だEnum.  それぞれの列挙型が列挙型のキーを列挙型値と結び付ける。 意味的にそのために、目録が不変のハッシュのように稼働する、しかしなぜならそれはパッケージを使うからStash 項目を持っているために、それは不変の宣言のセットを含んでいる typename パッケージとしてユーザーのネームスペースにそれ自身を提出する。 すなわち、

enum E <a b c>;
 

賛成の主として構文的な構文糖:だ

package E {
    constant a = 0;
    constant b = 1;
    constant c = 2;
}
 

(しかしながら、enum 宣言が余分の意味規則を供給する。)

このような不変の宣言は宣言された名前の使用が値が切望される値のために代理をすることを可能にする。 加えるに不変の宣言がマッチしてサブタイプとして振る舞う名前を開始するから、一つの値、列挙型が typename が必要とされるある特定の能力で typename として缶詰関数を調律する。 列挙の名前は全体として同じく typename だと見なされて、そして値のセットを表すために使われるかもしれない。 (我々が口頭で列挙を全体としてそれぞれの個人列挙型のペアから区別することを望むとき、それに注意する、それが使うと宣言されるにもかかわらず、我々は前者のために長期の「列挙」を使うenum キーワード。)

中にいるenum 宣言、キーは括弧で括られたリスト、あるいは同等の角括弧リストとして明示される:

my enum Day ('Sun','Mon','Tue','Wed','Thu','Fri','Sat');
my enum Day <Sun Mon Tue Wed Thu Fri Sat>;
 

値世代

値はデフォルトによって暗黙のうちに生み出される、しかし同じくであるかもしれない明示的に指定される. もし最初の値が特定されていないなら、それは0をデフォルトとする。 最初の値を指定するために、ペア表記法を使え(下を見ろ)。

もし宣言された枚挙 typename が大文字から始めるなら英字、値が得られるであろう列挙型Int あるいはStr 適切に。 もし枚挙 typename が小文字であるなら、列挙はネイティブの値のセットを表していると考えられる、それでデフォルト値型はそうだint あるいはbuf.

もし望ましいなら、ベース型は指定されることができる:

my bit enum maybe <no yes>;
my Int enum day ('Sun','Mon','Tue','Wed','Thu','Fri','Sat');
our enum day of uint4 <Sun Mon Tue Wed Thu Fri Sat>;
 

宣言された基底型は自動的に個体定数値にそれ自身を配る。 ネイティブでない型のために、列挙型オブジェクトは保証されているけれども、結局指定された型から生じて、そして変換できるに過ぎない。 シンボルを使うことによって、返された列挙型オブジェクトの実際の型はそれ自身列挙型だ。

Fri.WHAT    # Day, not Int.
+Fri        # 5
Fri.Numeric # 5
Fri ~~ Int  # True, because derived from Int
Fri.perl    # 'Day::Fri'
~Fri        # 'Fri' (only for numeric enums)
Fri.Stringy # 'Fri' (only for numeric enums)
Fri.Str     # 'Fri' (only for numeric enums)
Fri.gist    # 'Day::Fri' (used by say)
Fri.key     # 'Fri'
Fri.value   # 5
Fri.pair    # :Fri(5)
Fri.kv      # 'Fri', 5
Fri.defined # True
 

それ以外に、番号の貴重な列挙型が数とまったく同じように行動をする、他方文字列の貴重な列挙型が文字列とまったく同じように行動をする。 Fri.so その値が0よりむしろ5歳であるから、真だ。 Sun.so 偽だ。

ネイティブの値がそれ自身の型を知らないから、ネイティブの型に基づいた Enum がそれら値のためにだけ使われるかもしれない。

ネイティブの型の上のメソッドがそれらにコンテナの型を委任するから、ネイティブの型でタイプされた変数がどのメソッドを呼び出すべきか知るだろう:

my day $d = 3;
$d.key     # returns "Wed"
 

このような declarational フォームは常に都合が良いというわけじゃない;操作上(彼・それ)らの名前に戻っているネイティブの列挙型値を翻訳するために、あなたは列挙型型のを引き抜くことができるEnumMap そしてそれを裏返せ:

constant %dayname := Day.enums.invert;
%dayname{3} # Wed
 

枚挙型

枚挙型はそれ自身未定義の型オブジェクトだが、都合が良いメソッドを供給する:

Day.defined # False
3 ~~ Day    # True, using Day as a subset of Int
Day.enums   # map of key/value pairs
 

.enums メソッドが戻るEnumMap それは一定のハッシュ値としてあるいはペアのリストとして使用されるかもしれない:

my enum CoinFace <Heads Tails>;
CoinFace.enums.keys       # ('Heads', 'Tails')
CoinFace.enums.values     # (0, 1)
CoinFace.enums.kv         # ('Heads', 0, 'Tails', 1)
CoinFace.enums.invert     # (0 => 'Heads', 1 => 'Tails')
CoinFace.enums.[1]        # Tails => 1
 

枚挙 typename はそれ自身キー名あるいは値から強要演算子として使用されるかもしれない。 最初に引数はキーとして調べられる;もしそれが見つけられるなら、列挙型オブジェクトは返される。 もしキー名ルックアップが失敗するなら、値は(もしマッピングが1対1じゃないなら、 dups を持っているかもしれない)裏返されたマッピングテーブルを使って検索される:

Day('Tue')           # Tue constant, found as key
Day::('Tue')         # (same thing)

Day(3)               # Wed constant, found as value
Day.enums.invert{3}  # (same thing)
 

匿名の目録

anonymous enum ただそれぞれの文字列が連続的に増加する値で1対に変わることを確認する、それで:

%e = enum < ook! ook. ook? >;
 

同等の値:だ

%e = ();
%e<ook!> = 0;
%e<ook.> = 1;
%e<ook?> = 2;
 

匿名の目録のリターン値がであるEnumMap.enum キーワードはここでまだ宣言詞だ、それでリストはコンパイル時間に評価される。 威圧政治をそうするために使えEnumMap 実行時地図を受けとるために。

Pair からの作文

枚挙生成するものは対のためにリスト値を点検する、そしてそこで二人の値は明示的に次の値をセットする。 非対++ 前の値。 (Str と buf 型インクリメントは Perl 5 文字列が好きだ。) それ以来«...» quoter が書き入れとともに自動的にペア構文を認識する、我々はただ言うことができる:

my enum DayOfWeek «:Sun(1) Mon Tue Wed Thu Fri Sat»;

our Str enum Phonetic «:Alpha<A> Bravo Charlie Delta
                        Echo Foxtrot Golf Hotel India Juliet
                        Kilo Lima Mike November Oscar Papa
                        Quebec Romeo Sierra Tango Uniform
                        Victor Whiskey X-ray Yankee Zulu»;

enum roman (i => 1,   v => 5,
            x => 10,  l => 50,
            c => 100, d => 500,
            m => 1000);

my Item enum hex «:zero(0) one two three four five six seven eight nine
                  :ten<a> eleven twelve thirteen fourteen fifteen»;
 

枚挙宣言がコンパイル時間にそのリストを評価するとは、注意しろ、それでこのようなリストへの書き入れが実行時値に依存しないかもしれない。 さもなければ列挙型は定数じゃないだろう。 (もしこれがあなたが欲するものじゃないなら、普通の宣言使用方法を初期化しようとしろ::= スコープ宣言された読み取り専用値を作るために。)

あなたは列挙型型を輸入してもよい;ただ衝突しないシンボルだけが輸入される。 衝突している列挙型のカギが隠されて、そして型名であいまいさを排除されなくちゃならない。 あいまいな名前を使う Any 努力が致命的なコンパイルエラーをもたらすだろう。 (すべての衝突している値が隠される、ただ新しい(の・もの・人)、あるいは古い(の・もの・人)じゃない。) Any 明示 sub あるいは型定義が同一名のすべての輸入された列挙型のキーを隠す、しかし警告を作り出さないであろうならis redefined 含まれる。

匿名のミキシンロールが使うbut あるいはdoes

なぜならネイティブじゃないEnum 値が型、それらが右側で望ましいプロパティに名前をつけるために使われるかもしれないそれら枚挙を知っているbut あるいはdoes.  それでこれら:

$x = "Today" but Tue;
$y does True;
 

膨張しろ:

$x = "Today" but Day::Tue;
$y does Bool::True;
 

but そしてdoes 演算子が(彼・それ)らの右側でロールを期待する。 しかしながら、それ自身ロール型の列挙型型ではないbut そしてdoes ユーザーが列挙型型を供給するとき、演算子がそのことを知っている、もし属性が作成されている、そして読み取り専用が違っているなら、それは適切なアクセス機構を作成する匿名のミキシンロールの世代、読み書きを暗示する。 あなたが全部の(人たち・もの)あるいは特定の列挙型あるいは列挙全体を混ぜるかどうかについて、それは依存する:

$x = "Today" but Tue;       # $x.Day is read-only
$x = "Today" but Day;       # $x.Day is read-write
 

特定の列挙型オブジェクトを混ぜることはただ読み取り専用アクセス機構だけを暗示する。

$x = "Today" but Tue;
 

本当に何かが好むことを意味する:

$x = "Today".clone;
$x does anon role { method Day { Day::Tue } };
 

完全修飾形式は同じことをして、そして列挙型衝突の場合に有用だ:

$x = "Today" but Day::Tue;
 

メソッド名が静かであるとは、注意しろ.Dayしかしながら。 もしあなたが衝突しているメソッド名を混ぜることを望むなら、あなたは異なったメソッド名でミキシンに対してあなた自身の匿名のロールを持っているだろう。

なぜなら、威圧政治、あなたが同じく言うことができる(とき・から・につれて・ように)、目録が型名を供給するから:

$x = "Today" but Day(Tue);
$x = "Today" but Day(2);
 

それらの何の後にでも

$x.Day
 

戻るDay::Tue 標準の制約と強要での typenames としての関数が使う(すなわち、2を表している不変のオブジェクト)と将官と個別名両方。 従って、

$x ~~ Day
$x ~~ Tue
$x.Day == Tue
Day($x) == Tue
$x.Tue
 

すべては真に戻る、そして

$x.Wed
$x.Day == Wed
8 ~~ Day
 

すべて帰りの偽の。

フルの列挙を混ぜて、型が読み書き属性を生産する:

$x = "Today" but Day;       # read-write .Day
 

本当に何かが好むことを意味する:

$x = "Today".clone;
$x does anon role { has Day $.Day is rw }
 

もしすでにあるなら、何も起きないこと以外rw その名前の属性。

属性ではないが初期化したことに注意を払え。 もしそれが切望されるなら、あなたは物資を缶詰めにするWHENCE クロージャ:

$x = "Today" but Day{ :Day(Tue) }
$x = "Today" but Day{ Tue }  # conjecturally, for "simple" roles
 

トレイトを加える

枚挙宣言にトレイトを加えるために、宣言された名前の後にしかしリストの前にそれらを置け:

enum Size is silly <regular large jumbo>;
 

Exporting

目録を輸出するために、リストの直前に輸出トレイトを置け:

enum Maybe is export <No Yes Dunno>;
 

ロールを暗示する

目録が特定のロール、供給を暗示すると宣言することdoes 同じ場所で

enum Maybe does TristateLogic <No Yes Dunno>;
 

組込み目録

2つの組込み目録がそうだ:

our enum Bool does Boolean <False True>;
our enum Taint does Tainting <Untainted Tainted>;
 

それに注意しろBool そしてTaint ロール名ではなくが(彼・それ)ら自身ただロールを暗示するということだ、そして値が本当はサブセット型である列挙型Int不変のオブジェクトが(彼・それ)ら自身そのそれらを知っているけれども型の(こと・もの)だBool あるいはTaintそしてそのために容器正確に多メソッドディスパッチで使われる.

権限:呼び出し、低レベル.Bool どんな組込み型でもの上の強要、すべての組込み型がそうするからBoolean ロール、どちらか必要とする.Bool メソッド。 従って、言うことの間に、そこに1大差がある

    $x does Boolean;        # a no-op, since $x already does Boolean
    $x does Bool;           # create a $.Bool attribute, also does Boolean
 

Conditionals にの検定試験、返値、によって論理式の真実を評価しろ.Bool;それらがどのようにこれをするかは謎だが、そのそれら以外呼び出すのを避けるべき神秘的で、そしてプラットホーム依存の何かをしなくちゃならない.Bool 回帰的に結果に関しての.Bool.

決して値を比較しないそうすること「True」. ただブールのコンテキストでそれを使え。 まあ、ほとんど決して・・・。

もしあなたがブールのコンテキストについて露骨であることを望むなら、レベルが高い(人たち・もの)を使えso 関数あるいは? 演算子、どちらかが基礎をなしている接頭辞.Bool メソッド。 それ以来.Bool 常にジャンクションをつぶす、それでこれらの関数をしろ。 (従ってもしあなたが本当に自動装填に1群のブールを必要とするなら、値は、あなたはコンバートそれらに何か他の型にそんなものを持っているだろうBit それは後に論理値として使われることができる。 一般にそれは自動装填ブール値に意味をなさない、それで我々は後によりむしろより早くそれらをつぶすポリシーを持っている。)

雑多なルール

他の型のように名前と定数名、列挙型キー名がスカラー値を表しているスタンドアローンのトークンと解析されて、そして引数を探さない。 型名と異なり、、しかし定数名のように、列挙型キー名が定義された値を返す。 同じく型と異なり、そして列挙型型全体、キー名が応答しない民間企業と異なり、.() あなたが中に人と交わらないならCallable どうにかして。 (すなわち、言うことによって、 Tuesday に Wednesday を強制することは意味をなさないTue($wed).) 目録はポストによって宣言されたかもしれない。

our enum Maybe <OK FAIL>;
sub OK is redefined {...}
$x = OK;   # certainly the enum value
$x = OK()  # certainly the function
 

列挙型があるからOK関数OK ただ、決してリスト演算子形式でではなく、括弧を使って呼び出されるかもしれない。 (もし2つの列挙型値の上に共にそれらをキャンセルする衝突があるなら、関数はまだただ、列挙型の鍵が「汚染される」から、括弧で、呼び出されるかもしれない。)

.pick メソッド

型(そして有限のレンジのような多分ある特定の他の有限の、可算の型)が定義する列挙.pick その型の型オブジェクトの上のメソッド。 従って:

my enum CoinFace <Heads Tails>;
CoinFace.pick
 

戻るHeads あるいはTails 等しい蓋然性、を持っているそして

Month.pick(*)
 

順不同で月を返すだろう。 多分

StandardPlayingCards.pick(5)
 

Royal Flush を返すかもしれない、しかし Full House がずっとありそうだ。 選択が置換なしでされるから、それは決して Five Aces を返すことができない。 (もしそれが Five Aces を返すなら、歩き去る時間だ。 あるいは多分走れ。)

キー名あるいは値のリストから選んで、それらを得ることとして.enums 上記のメソッド。

Open 対 Closed Classes

デフォルトまでに、 Perl でのすべてのクラスは最終じゃない、そしてそれはあなたが潜在的にそれらから生じることができることを意味する。 それらは同じく、あなたがそれがあなたがしていることであることを明確にしていなければならないけれども、あなたがそれらにもっと多くのメソッドを加えることができることを意味するオープンだ:

augment class Mu {
    method wow () { say "Wow, I'm in the Cosmic All." }
}
 

さもなければあなたはクラス再定義エラーを得るだろう。 (同じく、完全に使用定義を置き換えるために「supersede" instead of " augment」・・・、しかし、コンパイラがすでに古い定義に基づいて最適化を約束したかもしれないから、それをするな。)

これらの宣言子のカジュアルな誤用を思いとどまらせるために、あなたが特別な宣言を頂上に置かないなら、それらはグローバルなクラスに関して許可されていない:

use MONKEY_TYPING;
 

最適化目的、6が使用によってトップレベルのアプリケーションに終了してクラスを完成させる権利を与える Perl のためにoo賛成のプラグマが、根本的なオブジェクト指向のエンジンについて:グローバルな意味規則を選択するという状態で

use oo :closed :final;
 

これはただその指定期間の末、メインコンパイル、を意味する閉への、そして最終の、アプリケーションのデフォルトを変える(CHECK 時間)オプティマイザは閉じるか、あるいは完成させるべき候補クラスを探すことを許される. けれども誰も(メインアプリケーションを含めて)が開かれて何でも滞在を分類することを要請することができる、あるいは nonfinal とクラス閉じ / finalizer はそれに名誉を与えなくちゃならない。

use class :open<Mammal Insect> :nonfinal<Str>
 

これらのプロパティは同じくクラス定義の上に指定されるかもしれない:

class Mammal is open {...}
class Insect is open {...}
class Str is nonfinal {...}
 

あるいはレキシカルにスコープ宣言されたプラグマによってクラス定義の周りに:

{
    use class :open;
    class Mammal {...}
    class Insect {...}
}
{
    use class :nonfinal;
    class Str {...}
}
 

個別のクラスが閉じられているか、あるいは最終であると宣言することに対して、構文がない。 アプリケーションはただオプティマイザが印がないクラスを閉じて、そして完成させるだけであることを要請するかもしれない。

主張

Perl 6 がすべてのオブジェクトが表示を持っていると想定するデフォルトまでにP6opaque.  これはトレイトでオーバーライドされるかもしれない:

class Mammal is repr(P6Hash) {...}
 

暗示的であるか、あるいは明示的かにかかわらず、主張は宣言の後にクラスの工面をすると見なされる、そしてオプティマイザはこの保証に基づいて最適化することが自由だ。 何とでも一緒の同じ型のオブジェクトを他の代表に列することは非合法だ。 もしあなたが実行時の指定された表示でオブジェクトが作成されることを可能にすることを望むなら、あなたは特にクラスを pessimize しなくちゃならない:

class Mammal is repr(*) {...}
 

augment それが本管の前にある限り、これをすることを許されるCHECK 時間、コンパイラがどのポイントをその最適化戦略に入れるかについて。 (それらがそうするかもしれないけれども)、コンパイラが実行時 pessimizations をサポートすることを必要とされない。 コンパイラが同じく共に最適な、そして pessimalのコードパスを生み出すかもしれなくて、そして実行時情報に基づいてどちらを走らせるべきか決めて、正しい意味規則と同じぐらい長い間保守される。

すべてのネイティブでない表示はスローされない例外を含んでいるかもしれない未定義の型オブジェクトをサポートすることを必要とされる(Failure オブジェクト);これが代わりの表示を使って実装されることができる間に、 Perl 6 はそのようにそれについて考えない. Perl 6 のすべての標準のオブジェクトは、もしそれらが定義されているなら、あるいは総称オブジェクト(普通名詞)としてそれらが定義されているか否かにかかわらず、特定のオブジェクト(適切な名詞)として使用されるかもしれない。 あなたは上の制約とは無関係にただでこの代表多様性を受けとる。

インタフェース一貫性

明示を宣言しないデフォルト、すべてのメソッドと submethods までに*% パラメータが暗黙を得るだろう*%_ パラメータがそれらのためにそれらがそれが好きかどうかについて意志表示した。 言い換えれば、メソッドが意外な名指された引数に許すすべて、それでそれnextsame 意味規則が首尾一貫して働く。

もしあなたマーククラス「is hidden「それ現在のクラスを隠すから」nextsame」意味規則、そしてついでに自(己・動)世代を隠すの*%_ パラメータ。 クラスがまだ呼び出されるかもしれない上に隠されたメソッド$obj.NameOfHiddenClass::yourmethod.

類似の効果が、言うことによって、派生クラスから達成されることができるhides Base 代わりにis Base.

内省

オブジェクトのためのメタメソッドが疑問の代名詞で大文字で名指される:

WHAT        the type object of the type, .gist returns MyClass()
WHICH       the object's identity value
WHO         the package supporting the object, stringifies to long name
WHERE       the memory address of the object
HOW         the metaclass object: "Higher Order Workings"
WHEN        (reserved for events?)
WHY         (reserved for documentation?)
WHENCE      autovivification closure
 

これらはメソッドとしてあるいは単項演算子として使用されるかもしれない:

$obj.WHAT   # method form of P5's ref
WHAT $obj   # unary form of P5's ref
 

これらはすべて実際は、真の演算子あるいはメソッドではなく、マクロだ。 もしあなたがさらに言語と必要から呼び出しまで外国のオブジェクトを得るならそ.WHERE メソッド、とあなたが言うことができる:

$obj."WHERE"
 

そしてもしあなたが前もってメソッド名を知らないなら、あなたはとにかく変数形式を使っているだろう:

$obj.$somemeth
 

それは同じくマクロを回避する。

もう1つのマクロがある:

DEFINITE    the object has a valid concrete representation
 

DEFINITE 賛成のデフォルトとしてのマクロサーブMu.defined メソッド。

今のところ Perl 6 はどのようにかに変化を与える権利のためにこれらすべてのマクロと文通することを取っておく^ フォームがお互いに関して定義される。 詳細、で.^ フォームがメタクラスのメソッドに最初の引数として自動的にインボカントを供給するだろう、他方他のフォームはあなたにこれほど明示的にパスするように要求する。

それに注意しろWHAT.gist アペンド() 名前に空虚さを示すために。 使用.perl 型オブジェクトからそのままの名前を得るために。 1(人・つ)を使え.Str.Stringyprefix:<~>あるいはinfix:<~> 何に関してでも戻ることについての Perl5ish 意味規則、空の文字列、(警告で)のために型オブジェクトを手に入れるために。 (Perl 6 で、「undef」がない;型オブジェクトがその代わりにタイプされた undefs を供給する。)

一般に、普通のコードでのこれらの uppercasedなアクセス機構の使用は Something Very Strange が起こっているという赤いフラグであるべきだ。 (従って allcaps) たいていのコードが暗黙的にこの情報を利用する Perl 6 の演算子を使うべきだ。 例えば、その代わりにの

$obj.WHAT eq 'Dog()'
$x.WHICH === $y.WHICH
$obj.WHAT.bless(%args)
 

あなたは通常ちょうど欲する:

$obj ~~ Dog
$x === $y
$obj.bless(%args)
 

すべてのクラスがそうしたHOW クラス(あるいは他のメタオブジェクトプロトコル)がクラスのオブジェクトを実装することに対して、あなたにすべてのメタデータプロパティをほのめかさせるあなたにクラスのメタオブジェクトをほのめかさせる関数 / メソッド:

MyClass.methods()           # call MyClass's .methods method (error?)
MyClass.HOW.methods($obj)       # get the method list of MyClass
 

^ メタ構文が同等であるそうすること.HOW

MyClass.HOW.methods($obj)   # get the method list of MyClass
^MyClass.methods($obj)      # get the method list of MyClass
MyClass.^methods()          # get the method list of MyClass
 

クラスのそれぞれのオブジェクトが同じくそうした.HOW あるいは.^ メソッド:

$obj.HOW.methods($obj);
$obj.^methods();
 

(もしあなたがクラス・ベースよりむしろプロトタイプベースの OO を使っているなら、あなたはオブジェクト形式、すべてのそのようなオブジェクトから関数をそれ自身のクラスとして使用しなくちゃならない。)

クラストレイトが次のものを含む:かもしれない

identifier  { :name<Dog> :auth<http://www.some.com/~jrandom> :ver<1.2.1> }
    name      Dog
    authority http://www.some.com/~jrandom
    version   v1.2.1
author        Joe Random
description   This class implements camera obscura.
subject       optics, boxes
language      ja_JP
licensed      Artistic|GPL
parents       list of parent classes
roles         list of roles
disambig      how to deal with ambiguous method names from roles
repr          P6opaque, P6hash, P5hash, P5array, PyDict, Cstruct, etc.
 

これらは標準的な Perl 6 Meta - オブジェクト Protocol のためだ、しかし他の MOPs が他のトレイトを定義するかもしれない。 識別子はおそらく完全にアクセスされるべきである.WHO 型ネームスペースがどのように長い間に進展するかについて、依存しているそれ自身のオブジェクトメソッドを持っているかもしれないどんなケースでものオブジェクト。 これらについて項目が実際に部分的にである.HOW オブジェクトとそれはパッケージとプロトタイプオブジェクトに戻っている委任が MOP 次第であるということだ。 (同じく匿名のクラスが匿名のパッケージを持っていて、そして、どの非グルに重要な何かを生産する可能性が高いケース文字列化ではないで、オブジェクトのプロトタイプを作るかもしれないことに注意を払え。)

.^parents デフォルトによってのメソッドがそうしようとしている(しかし含まない)すべての親の平らになったリストを返すCool あるいはAnyMRO (ディスパッチ)オーダーでソートした。 他の選択がそうだ:

:local              just returns the immediate parents
:local($n)          return $n levels
:excl               exclude Cool and Any (the default)
:all                include Cool and Any
:tree               the inheritance hierarchy as nested arrays
 

.^methods メソッドがメソッド - 記述子を含んでいることを返す:

name                the name of the method
signature           the parameters of the method
as                  the coercion type of the method
proto               whether this method governs a set of multi methods
do                  the method body
 

.^methods メソッドがあなたにあなたが平らになっているか、あるいは階層的なビューを見ることを望むかどうか、あなたが私的なメソッドなどに興味を持っているかどうか明示させる選択者パラメータを持っている。

:local              only methods defined in the current class
:local($n)          out $n levels
:excl               exclude Cool and Any (the default)
:all                include Cool and Any
:tree               methods by class structure (inheritance hierarchy)
:private            include private methods
 

それが、内省から主に1セット外の世界(クラスが、結局のところ、すでにそれ自身の構造を知っている)、による使用のための重要性multi メソッドがシングルであるために提供されるproto メソッド。 あなたは使う必要がある.candidates それに関してさらにそれを分類するために。

.^attributes メソッドがリストを返すのAttribute これらのようにメソッドを持っているオブジェクト:

name
type
scope
rw
private
has-accessor
build
readonly
get_value($obj)
set_value($obj, $new_value)
 

それに注意するAttribute ではないが型の特定のオブジェクトに、しかしむしろ型にそれ自身をタイした。 それはなぜかだget_value そしてset_value 最初の定位置パラメタとして実際のオブジェクトを受け取る必要がある。

[推測:もしそれがメタクラスあるいは実装するべき表示に適していないならset_value そしてget_valueそれこれらのメソッドが呼び出されるとき、役立つエラーメッセージをもって死ぬかもしれない。]

set_value そしてget_value 属性のプライバシーを侵害して、そしてそれで注意して、そしてユーザー自身の危険で使われるべきだ。

.^attributes 同じくパラメータをとる:

:local              only methods defined in the current class
:local($n)          out $n levels
:excl               exclude Cool and Any (the default)
:all                include Cool and Any
:tree               attributes by class structure (inheritance hierarchy)
 

厳密に言えば、メタメソッドが好む.isa().does()そして.can() メタオブジェクトを通して呼び出されるべきだ:

$obj.HOW.can($obj, "bark")
$obj.HOW.does($obj, Dog)
$obj.HOW.isa($obj, Mammal)
 

あるいは

$obj.^can("bark")
$obj.^does(Dog)
$obj.^isa(Mammal)
 

ただAny 人たちにあなたに近道を与える:

$obj.can("bark")
$obj.does(Dog)
$obj.isa(Mammal)
 

これら、は、もちろん、サブクラスでオーバーライドされるかもしれない、それで、あなたがオーバライドを考慮に入れることを望まないなら、短縮フォームを使うな。 一般に、Any ただ、およそ1つの個別のオブジェクトを理論的に考えるとき、よい読後感を与えたそれらのメタメソッドだけを委任するだろう。 メソッドが好きである Infrastructural .^methods そして.^attributes それほど、委任されない$obj.methods 失敗する。

スマートマッチしろ:

$obj ~~ Dog
 

実際は呼び出し:

$obj.HOW.does($obj, Dog)
 

それは真のもしだ$obj 「そうする」あるいは「isa」Dog (あるいは「isa」それが「する」何かDog). もしDog サブセット、追加の何もだwhere 制約が同じく真を評価しなくちゃならない。

Perl 5 の場合と異なりどこ(で・に)か.can シングルを返すCode オブジェクト、6が機種である Perl .^can 名前とマッチする、すべてを含めて可能性を自動的にロードして、そして wildcarded したルーチンのセットのために「歩行」イテレータを返す。 特に、.^can どんなクラスパッケージでものを尋問するCANDO クラスで自(己・動)ロード可能なメソッドだと見なされるはずだ、たとえそれらであるとしてもまだ宣言されなかった名前のためのメソッド。 ロール合成が時々、もしそれが必要とされて、そしてクラスあるいはそのロールの1つによって供給されなかったなら、スーパークラスが特定の名前のメソッドを供給するかどうか決定するこの能力に頼る。

ストップするための動機づけでCool そしてAny デフォルトのそばに人たちの1人からの最初の導出が本当にユーザーがほとんどいつも型階層のルートクラスであると考えるものであることがある。 それの外のメソッドは本当にすべての型の向こう側に識別可能な Perl 6 の辞書の部分だ。 従ってもしあなたが、例えば、言うなら$object.sort あるいは$object.arctanあなたユーザーの型階層を越える傾向があるよく知られている文化的なコンセプトに訴えている. ユーザーが $object.^methods を求めるとき、デフォルトまでにこのようなメソッドをリストすることはどちらかと言うといらいらさせる。

我々が言うとき、それに注意する「Cool そしてAny」上に、我々はそれら、そんなものの外で本当に、何と同様でも、それらの型に型を意図するけれどもMu あるいはJunction.  けれどもユーザーが一般にとにかくそれらの型から生じているべきじゃない。

Autovivifying オブジェクト

WHENCE オブジェクトのプロパティはその autovivifying クロージャだ。 Any の未定義のプロトタイプオブジェクトがいい加減に適切な型のオブジェクトを作ることができるこのようなクロージャを振る舞うかもしれない。 クロージャが最終的に評価されるとき、そうすることは引数に対応している引数リストを返すために期待される.bless 呼び出し。 例えば、CANDO 作ることの代わりの、ルーチンDog オブジェクトが直接、その代わりに何かを同種のものリターンすることができた:

Dog but WHENCE({ :name<Fido> })
 

もしオブジェクトが autovivified される必要があるなら、それはクロージャを動かす。 どんなイニシャライザがオリジナルのレキシカルスコープで利用可能であったとしてもクロージャの缶詰キャプチャ。

上の(人たち・もの)の短縮フォームは簡単にだ:

Dog{ :name<Fido> }
 

このフォームは同じくいい加減に評価される:

my $dog = Dog{ :name<Fido> };
defined $dog or say "doesn't exist";  # Fido doesn't exist
$dog.wag()                            # Fido wags his tail
 

typename がたまたまそれが作ろうと試みることを必然的に必要とする autovivifying しているロールであるときしゃれを言うロールとしての同一名のクラス. ロールがそれ自身のものの上にクラスの役をするのに十分完全かどうかについて、これが成功するかどうかが依存する。 このような試みが成功するであろうかどうかにかかわらず、それがただ今までにそうに引数として使用されるだけであるのと同じぐらい長い間ロールのためにいい加減な型オブジェクトを定義することは常に完全に素晴らしいblessそれ以来bless ただそのクロージャをロールのを作成するだけであるために使っているだろうBUILD 完全な新しいクラスのコンテキストでの引数。 (もちろん、首尾一貫しないか、あるいは不完全なクラス作文がその後失敗するかもしれない、そして実際上に述べた不完全なロール autovivification は、クラス作文のポイントに失敗することによって、実装される可能性が高い。)

引数として使用されてそれほどいつ注意するからメソッドが好むbless型 autovivifying に適切な(人たち・もの)によってだけされるオブジェクトが十分にいい加減だBUILD ルーチン。 それはエネルギーを作ることを浪費しないDog そのオブジェクトの属性が後に実際のオブジェクトにコピーされなければならないであろうオブジェクト。 (どちらの上に、このような実装は型オブジェクトを不完全なロールを初期化するために使うことを不可能にするだろう。)

オブジェクト autovivification 構文はリテラルの名指された型でだけ働く、それで間接参照がそうしなくちゃならない何でもいっそう明示的に書かれる:

::($dogproto){ :name<Fido> }
$dogproto but WHENCE({ :name<Fido> })
$dogproto.WHAT{ :name<Fido> }
 

シンボルのこの構文、ルックアップと対照的なそれで注意するDog 実装が決勝戦を必要とする:: 添え字の前に:

Dog::{$varname}