Hatena::ブログ(Diary)

Islands in the byte stream

2011-02-24

"Constant subroutine foo::bar redefined" を抑制する

普通のサブルーチンの再定義は "no warnings 'redefined'" "no warnings 'redefine'" で警告を抑制できるわけですが、定数サブルーチンは警告のでる条件がちょっと違います。具体的には、再定義警告は以下のいずれかの条件を満たすときです*1

  • use warnings 'redefine' (or -w switch) のもとである
  • 対象が定数サブルーチンかつ再定義しようとしている値が異なる

例:

#!perl -w
use strict;

use constant FOO => 10; # first definition

use constant FOO => 10; # redefine without warnings

use constant FOO => 20; # redefine WITH warnings

constant.pmを使っているかぎり、この警告を抑制するには$SIG{__WARN__}を潰すしかありません。しかしこれは最後の手段にすべきです。そもそも定数を書き換えるべきではないからこそ強制的に警告をだすようになっているのですから。

値を書き換えたいときは定数サブルーチンでなく通常のサブルーチンとして定義するほうがいいでしょう。定数サブルーチンでなくする方法はいくつかあります。

以下のコードはその一例です:

# (1) returnを使う
sub foo() { return 42 }

# (2) 値を参照可能な状態にしておく
my $foo = 42;
sub foo() { $foo }
# cf. BEGIN{ my $foo = 42; *foo = sub(){ $foo } }

DQNEODQNEO 2015/03/24 01:56 no warnings 'redefined'
ではなくて、
no warnings 'redefine'
が正しいのではないでしょうか。

gfxgfx 2015/03/24 07:50 たしかに!なんとまあ…4年後しのバグフィクスとはw ありがとうございます。

トラックバック - http://d.hatena.ne.jp/gfx/20110224/1298524073