簡體   English   中英

Perl 6 多方法永遠不會匹配預期的簽名

[英]Perl 6 multi methods never match expected signature

我有一個有兩個多方法的類( multi submit )。

我這樣稱呼我的 multi:

$perspective.submit(:message($message.content));

哪個被運送到我的班級:

my $perspective-api = API::Perspective.new(:api-key(%*ENV<PERSPECTIVE_API_KEY>));

proto method submit (|) {*}

multi method submit(Str :$message!, MODEL :@models = TOXICITY) {
    my $score = $perspective-api.analyze(:@models, :comment($message));
    say @models Z=> $score<attributeScores>{@models}.map: *<summaryScore><value>;

multi method submit(Str :$name!, MODEL :@models = TOXICITY) {
    my $score = $perspective-api.analyze(:@models, :comment($name));
    say @models Z=> $score<attributeScores>{@models}.map: *<summaryScore><value>;
}

但是我總是得到以下回應:

Died because of the exception:
    Cannot resolve caller AUTOGEN(Rose::ContentAnalysis::Perspective:D: :message(Str)); none of these signatures match:
        (Rose::ContentAnalysis::Perspective: Str :$message!, MODEL :@models = MODEL::TOXICITY, *%_)
        (Rose::ContentAnalysis::Perspective: Str :$name!, MODEL :@models = MODEL::TOXICITY, *%_)

盡管我的命名參數 ( :message ) 是Str要求的並且@models聲明了默認值。

多分派工作分兩個階段:

  • 考慮位置參數的數量及其類型
  • 如果有任何where子句、命名參數或子簽名,則對簽名進行測試綁定以查看是否匹配

如果候選人因任何原因未能綁定,則第二階段將拒絕候選人。 一個這樣的原因,我相信這里問題的原因,是默認值輸入錯誤。 例如,在:

multi m(:@x = "not-an-array") { }
m()

我們得到一個錯誤:

Cannot resolve caller m(...); none of these signatures match:
    (:@x = "not-an-array")
  in block <unit> at -e line 1

但將其更改為:

multi m(:@x = ["an-array"]) { }
m()

工作正常。 (請注意,雖然默認值使用= ,但它實際上是一個綁定,而不是一個賦值。)

在問題的情況下是這樣的:

MODEL :@models = TOXICITY

查看代碼取自的模塊源代碼,我看到:

enum MODEL is export (
        <TOXICITY SEVERE_TOXICITY TOXICITY_FAST IDENTITY_ATTACK
        INSULT PROFANITY SEXUALLY_EXPLICIT THREAT FLIRTATION
        ATTACK_ON_AUTHOR ATTACK_ON_COMMENTER INCOHERENT INFLAMMATORY
        LIKELY_TO_REJECT OBSCENE SPAM UNSUBSTANTIAL>
);

因此 TOXICITY 只是一個Int ,但預期的是MODEL值的類型化數組。

因此,如果你這樣做:

multi method submit(Str :$message!, MODEL :@models = Array[MODEL](TOXICITY)) {

它應該工作。

我看到兩個問題。

一種是您有兩個相同的方法,除了一個命名參數的名稱。

命名參數可以有別名:

#                       V--------------V
multi method submit(Str :name(:$message)!, MODEL :@models = TOXICITY) {
    my $score = $perspective-api.analyze(:@models, :comment($message));
    say @models Z=> $score<attributeScores>{@models}.map: *<summaryScore><value>;
}

注意:$message:message($message)縮寫


現在討論實際上阻止您的代碼工作的問題。

@models是一個Positional ,但您在簽名中為其分配了一個奇異值。

為其分配一個Positional ,它可以工作:
(在這種情況下,由於MODEL類型聲明,它必須是Array[MODEL]類型。)

#                                                           V---------------------V
multi method submit(Str :name(:$message)!, MODEL :@models = Array[MODEL](TOXICITY,)) {
    my $score = $perspective-api.analyze(:@models, :comment($message));
    say @models Z=> $score<attributeScores>{@models}.map: *<summaryScore><value>;
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM