単一のパイプを使用するとどうなりますか '|' 関数の引数で行う?


82

たとえば、次のコードを考えてみましょう。

phpinfo(INFO_MODULES | INFO_ENVIRONMENT | INFO_VARIABLES);

単一の引数が使用されていますが、単一のパイプ記号で区切られたオプションのリストを提供しています。

  • 関数の引数値は正確に何が起こっているのですか?
  • 同じことを自分の関数で使用できますか?
  • そうですか、代わりに配列を渡すと言うよりも、これには利点がありますか?

これはORのビット単位のバージョンであり、通常のバージョンには2つのパイプがあります。
adeneo 2012

32
ご存知のように、一部のコメンテーターがユーザーの質問への意欲を軽視していることを乗り越えることはできません... 21万人の担当者がいるユーザーがそれに答えるのに必要なところまで!
nickhar 2012

5
質問をしていないSOで評判が5000を超えるユーザーは、本当に質問がないのでしょうか、それとも質問をすることを弱点の兆候と考えているのでしょうか。
ピーター

15
また、記号を検索するのは難しいことも理解しましょう。
Levi Morrison

9
@nickhar ..そして、そのドキュメントページにたどり着くには、そもそも特定の用語に精通している必要があります。これは、どういうわけか質問の
要点

回答:


136

ビット演算子

ビットごとの演算子は、関連する値のビットを変更します。ビット単位では、OR基本的に、左引数と右引数の両方の各ビットをOR演算します。例えば:

5 | 2

次のようにビット/バイナリに変換されます:

101 | 10

その結果、次のようになります。

111

理由:

1 || 0 = 1
0 || 1 = 1
1 || 0 = 1

そして、7の表現である整数として、次の場合に正確に得られます。

echo 5 | 2;

エディー・イザードの言葉で...旗!

Ignacioが述べているように、これは複数のフラグを組み合わせる方法としてPHP(およびその他の言語)で最も頻繁に使用されます。各フラグは通常、定数として定義され、その値は通常、異なるオフセットで1ビットのみを表す整数に設定されます。

define('FLAG_A', 1); /// 0001
define('FLAG_B', 2); /// 0010
define('FLAG_C', 4); /// 0100
define('FLAG_D', 8); /// 1000

次に、ORこれらを一緒にすると、それぞれが独自のビットオフセットで動作し、衝突することはありません。

FLAG_A | FLAG_C

翻訳:

1 | 100

したがって、最終的にオンになります。

101

これは整数5を表します。

次に、すべてのコード(設定されているさまざまなフラグに反応するコード)は次のようになります(ビット単位を使用AND)。

$combined_flags = FLAG_A | FLAG_C;

if ( $combined_flags & FLAG_A ) {
  /// do something when FLAG_A is set
}

if ( $combined_flags & FLAG_B ) {
  /// this wont be reached with the current value of $combined_flags
}

if ( $combined_flags & FLAG_C ) {
  /// do something when FLAG_C is set
}

結局のところ、名前付き定数を使用することで読みやすくなり、文字列や配列ではなく整数値に依存することで一般的に最適になります。定数を使用するもう1つの利点は、使用時にタイプミスがあった場合、コンパイラーが警告を通知してスローするのに適した状況にあることです。文字列値が使用されている場合、何かが間違っていることを知る方法がありません。

define('MY_FLAG_WITH_EASY_TYPO', 1);

my_function_that_expects_a_flag( MY_FLAG_WITH_EASY_TPYO );

/// if you have strict errors on the above will trigger an error

my_function_that_expects_a_flag( 'my_string_with_easy_tpyo' );

/// the above is just a string, the compiler knows nowt with 
/// regard to it's correctness, so instead you'd have to
/// code your own checks.

5
素晴らしい投稿のために+1。私はこれに頭を悩ませるのに苦労していましたが、あなたの説明と例は、PHPのドキュメントを読んだばかりの場合よりもはるかに簡単に理解するのに役立ちました。どうもありがとうございました。
不可解なツ

3
@cryptic心配ありません-結局のところ、名前を付けることができないものを検索するのはかなりトリッキーです-Googleだけが説明と例の段落を検索用語として受け入れた場合:)
Pebbl 2012

4
素晴らしい説明と例!+1
Sablefoste 2012

16

複数のフラグのビットごとのORである引数を渡しています。演算子はどこでも使用できます。


10
@Ignacioさん、SOの全員がプログラミングの専門家であるとは限らず、ドキュメントをどこから始めればよいかさえ知っているわけではないことを覚えていただき、ありがとうございます。
Sablefoste 2012
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.