4

この本全体で使用されているいくつかのスカラーをエクスポートするモジュールを作成することで、いくつかのPerl のベスト プラクティスを簡単に実行できるようにしようとしています。Constants特に、 は$EMPTY_STRING、私が作成するほぼすべての Perl スクリプトで使用できます。私が望むのは、これらのスカラーを自動的にエクスポートして、各スクリプトで明示的に定義せずに使用できるようにすることです。

#!perl
package Example::Constants;

use Exporter qw( import );
use Readonly;

Readonly my $EMPTY_STRING => q{};
our @EXPORT = qw( $EMPTY_STRING );

使用例:

#!perl
use Example::Constants;
print $EMPTY_STRING . 'foo' . $EMPTY_STRING;

上記のコードを使用すると、エラーが発生します。

Global symbol "$EMPTY_STRING" requires explicit package name

Readonly宣言を次のように変更すると:

Readonly our $EMPTY_STRING => q{}; # 'our' instead of 'my'

エラーは次のようになります。

Attempt to reassign a readonly scalar

これは mod_perl では不可能ですか?

4

3 に答える 3

4

私は Readonly モジュールの作者です。Readonly の次のバージョンでは、特にこの問題のために mod_perl がサポートされる予定です。

これで問題が解決しないことはわかっていますが、...まあ、私はそれに取り組んでいます:-)

-- エリック

于 2009-04-13T21:59:24.850 に答える
4

4 つの問題がありました。

  1. strictandwarningsプラグマ を含めていませんでした
  2. baseプラグマを介してエクスポーターを含めること@ISAをお勧めします(設定するため)
  3. パッケージ変数 (つまりour、変数) のみをエクスポートできます
  4. モジュールは真の値で終わる必要があります

これが修正されたモジュールです。

package Example::Constants;

use strict;
use warnings;
use base 'Exporter';
use Readonly;

Readonly our $EMPTY_STRING => q{};
our @EXPORT = qw( $EMPTY_STRING );

1;

うーん、読み取り専用に割り当てようとしているのを少し見逃していました。モジュールが複数回読み込まれているようです。mod_perl には、スクリプト自体とは別にモジュールをロードするメカニズムがあると思います。この読み込みは 1 回しか行われないため、使用する必要があります。

于 2009-04-10T00:57:41.787 に答える
1

テストに便利な mod_perl インスタンスがないため、これらの提案をテストできません。彼らが成功することを願っています。

Scalar::Util::readonlyを使用して、変数が既に読み取り専用としてマークされているかどうかを確認してみてください。

#!perl
package Example::Constants;

use Exporter qw( import );
use Readonly;
use Scalar::Util qw(readonly);

our $EMPTY_STRING;
our @EXPORT = qw( $EMPTY_STRING );

if ( !readonly( $EMPTY_STRING ) ) {
    Readonly $EMPTY_STRING => q{};
}

あなたも試すことができますuse vars

#!perl
package Example::Constants;

use Exporter qw( import );
use Readonly;
use vars qw( $EMPTY_STRING );

Readonly $EMPTY_STRING => q{};
our @EXPORT = qw( $EMPTY_STRING );

typeglob 定数を使用することもできます。

#!perl
package Example::Constants;

use Exporter qw( import );
use Readonly;

our $EMPTY_STRING;
*EMPTY_STRING = \q{};
our @EXPORT = qw( $EMPTY_STRING );

テクニックの大きな制限 (パッケージ グローバルが必要) はここでは問題にならないため、typeglob 定数の使用は完璧に思えます。

于 2009-04-12T06:43:49.410 に答える