RubyのArray.new(5,'default')っぽいことをPerlでする試み

始まり

Rubyを勉強し始めていて、RubyArray.new(5,'default') などとすると、要素数5の配列が生成されるが、これら1つ1つの要素は同じオブジェクトIDを所持している為 a[0].upcase! などとすると全ての要素が変更される事を知った。

普段書いているのはPerlなので、Perlではどのようにするとこれが再現できるかを考えてみた。

試みる

id:mackee_w さんに拾っていただき試みが始まる。

そして書いたコード

#!/usr/bin/env perl
use strict;
use warnings;
use DDP { deparse => 1 };

my $hoge = {hoge => "saru"};

my @hoge = map { $hoge } (1..10);

p @hoge;

さらに別の方法が議論される。

そして書かれたコード達

#!/usr/bin/env perl
use strict;
use warnings;
use DDP { deparse => 1 };

my $hoge = {hoge => "saru"};

#my @hoge = map { $hoge } (1..10);
#
#p @hoge;

my @array =  ($hoge) x 10;

p @array;
use Data::Dumper;
my $h = { hoge => "huga" };
warn Dumper [ ($h) x 10 ];

解説

PerlではオブジェクトIDのようなものはリファレンスそのものなので、リファレンスをリストコンテキストでn回増やし配列に代入するとこのような事が可能だった。

mapの例は (1..10) で範囲を表して同じようなことを行っている。

感想

Perlで考えてみると実際の処理が解ってくる気がした。