0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

Perl 6Advent Calendar 2017

Day 19

Perl 6で動的に名前付き引数を指定する

Last updated at Posted at 2017-12-23

こんにちは19日目の投稿になります。

今日は、Perl 6で動的に名前付き引数を指定する方法を紹介しようと思います。

下記は、挨拶を行うプログラムです。
perl6で名前付き引数に対して代入を行う場合は、通常name => "ラリー" (#1)や、:name("ラリー") (#2)といった形で代入を行います:

use v6;                                                                                                                    
use Test;                                                                                                                  
                                                                                                                           
sub greeting(Str :$name = "noname", Int :$hours = 8 --> Str) {                                                             
    sprintf("こんにちは %s さん。今日も %d 時間労働頑張るぞい。\n", $name, $hours);                                        
}                                                                                                                          
                                                                                                                           
is greeting, "こんにちは noname さん。今日も 8 時間労働頑張るぞい。\n"; # ok                                                  
is greeting(name => "ラリー"), "こんにちは ラリー さん。今日も 8 時間労働頑張るぞい。\n"; # ok (#1)                                 
is greeting(:name("ラリー"), :hours(12)), "こんにちは ラリー さん。今日も 12 時間労働頑張るぞい。\n"; # ok (#2)     

done-testing;                

ここで、ラリーさん以外にも挨拶を行うことを考えましょう。下記のような名前-労働時間のペアを新たに追加することを考えます:

  • ザ・企業戦士のラクダさんは20時間労働
  • 時短労働のカメリアさんは4時間労働
  • 定時退社しないと気が済まないパンプキンさんは7時間労働

そうすると、コードは下記のようになります:

is greeting(:name("ラリー"), :hours(8)), "こんにちは ラリー さん。今日も 8 時間労働頑張るぞい。\n"; # ok (※ラリーさんは2人いる)
is greeting(:name("ラリー"), :hours(12)), "こんにちは ラリー さん。今日も 12 時間労働頑張るぞい。\n"; # ok
is greeting(:name("ラクダ"), :hours(20)), "こんにちは ラクダ さん。今日も 20 時間労働頑張るぞい。\n"; # ok                      
is greeting(:name("カメリア"), :hours(4)), "こんにちは カメリア さん。今日も 4 時間労働頑張るぞい。\n"; # ok                   
is greeting(:name("パンプキン"), :hours(7)), "こんにちは パンプキン さん。今日も 7 時間労働頑張るぞい。\n"; # ok 

ちょっと冗長じゃないかなあと思った方もいるかと思います。
実はPerl6では引数の内容をいったん別の変数に格納しておいて、あとから使うこともできます。
そうするともっと簡潔に書けそうですよね。
具体的には、|とハッシュを使って上記のコードと等価なコードを書くことができます:

my @options = [ 
    {:name("ラリー")},                                                                                                          
    {:name("ラリー"), :hours(12)},                                                                                         
    {:name("ラクダ"), :hours(20)},                                                                                         
    {:name("カメリア"), :hours(4)},                                                                                        
    {:name("パンプキン"), :hours(7)}                                                                                       
];                                                                                                                         
                                                                                                                           
for @options -> %option (Str :$name = "noname", Int :$hours = 8) {                                                                        
    is greeting(|%option), "こんにちは $name さん。今日も $hours 時間労働頑張るぞい。\n"; # ok (#1)
}  
  • この例では、|%optionでHashを名前付き引数に変換しています。 (#1)

どうでしょうか。だいぶ簡潔に書けるようになったと思います。
Pairにおいても同等のことができます。詳しくは次のページを参照ください: https://docs.perl6.org/type/Signature#Positional_vs._Named

以上、19日目の投稿でした。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?