19

Perl 5.10以降、$_明示的にmy $_;またはgiven / when構成内で、コンテキスト変数を字句的にスコープすることが可能になりました。

誰かが語彙の良い使い方を見つけました$_か?それはどんな構成もより単純/より安全/より速くしますか?

それがより複雑になる状況はどうですか?字句$_はコードにバグを導入しましたか?(書き込み先の制御構造体$_は、スコープ内にある場合は字句バージョンを使用するため、サブルーチン呼び出しが含まれている場合(動的スコープが失われるため)、コードの動作が変わる可能性があります)

$_最後に、レキシカルとして、グローバルとして、またはまったく問題にならない場合を明確にするリストを作成したいと思います。


注意:perl5-5.24これらの実験的機能の時点では、perlの一部ではなくなりました。

4

4 に答える 4

8

IMO、字句から出てくる素晴らしいことの1つ$_は、新しい_プロトタイプシンボルです。

これにより、1つのスカラーを取るように、または何も指定されていない場合は取得するように、サブルーチンを指定できます$_

したがって、書く代わりに:

sub foo {
    my $arg = @_ ? shift : $_;

    # Do stuff with $_
}

私は書くことができます:

sub foo(_) {
    my $arg = shift;

    # Do stuff with $_ or first arg.
}

大きな変更ではありませんが、その動作が必要な場合は、はるかに簡単です。ボイラープレートの取り外しは良いことです。

もちろん、これにはいくつかのビルトイン(例chr)のプロトタイプを変更するというノックオン効果があり、一部のコードが破損する可能性があります。

全体的に、私は字句を歓迎し$_ます。これにより、偶発的なデータの改ざんや関数間の奇妙な相互作用を制限するために使用できるツールが得られます。関数の本体で使用することにし$_た場合、それを字句化することで、$_呼び出すコードがコードの呼び出しで変更されないことを確認できます。

動的スコープは興味深いものですが、ほとんどの場合、字句スコープが必要です。これに周りの合併症を追加し$_ます。単純に行うのはお勧めできません。代わりlocal $_;に使用するのが最善であるという悲惨な警告を聞いたことがあります。for ( $foo ) { }Lexicalized$_は、なんらかの方法でローカライズしたときに、100回のうち99回欲しいものを提供してくれます$_。Lexical$_は、優れた利便性と読みやすさの機能をより堅牢にします。

私の仕事の大部分はperl5.8で動作しなければならなかったので$_、大規模なプロジェクトで字句を使って遊ぶ喜びはありませんでした。しかし、これは安全に利用するのに大いに役立つと感じています$_。これは良いことです。

于 2010-08-04T16:49:12.900 に答える
3

モジュールをいじっているときに発生した問題(バグは言葉が強すぎる)をかつて見つけました。Inlineこの単純なスクリプト:

use strict qw(vars subs);
for ('function') {
    $_->();
}
sub function {
  require Inline;
  Inline->bind(C => <<'__CODE__');
void foo() 
{
}
__CODE__
}

Modification of a read-only value attempted at /usr/lib/perl5/site_perl/5.10/Inline/C.pm line 380.エラーメッセージで失敗します。モジュールの内部の奥深くには、Inline変更したいサブルーチンがあり、$_上記のエラーメッセージが表示されます。

使用する

for my $_ ('function') { ...

または、宣言することmy $_は、この問題に対する実行可能な回避策です。

Inlineこの特定の問題を修正するために、モジュールにパッチが適用されました)。

于 2010-08-04T18:44:57.317 に答える
1

[理論的根拠:通りすがりのperlの新規参入者のための簡単な要約を含む短い追加の回答。「perllexicaltopic」を検索すると、ここで終わる可能性があります。]

今(2015年)までに、語彙トピック(my $_およびいくつかの関連機能)の導入により、最初に意図しない動作を検出するのが困難になり、実験的なものとしてマークされ、非推奨の段階に入ったことは一般的な知識だと思います。


の部分的な要約 #RT119315:1つの提案はuse feature 'lextopic'; 、新しい字句トピック変数を利用するようなものでした: $^_。もう1つのポイントは、「トピック化演算子の暗黙の名前...以外」は、明示的に字句関数($_たとえば、字句mapまたは)と組み合わせると最も効果的に機能するということlmapでした。これらのアプローチがどういうわけか救済を可能にするかどうかgiven/whenは明らかではありません。実験段階と減価償却段階の死後の世界では、おそらく何かがCPANの川に住んでしまう可能性があります。

于 2015-03-09T15:15:23.177 に答える
0

ここでは問題はありませんが、Perlの魔法に関しては、「聞かないで、言わないでください」というポリシーに従う傾向があります。つまり、ルーチンは通常、副作用として非字句データをねじ込むピアに依存したり、それらを許可したりすることは期待されていません。

時折参照するためにCamelを説明する5.6を使用しながら、perlのさまざまな5.8および5.10バージョンに対してコードをテストしました。問題はありません。私のもののほとんどはもともとperl5.8.8のために行われました。

于 2010-08-04T07:11:21.487 に答える