Was bedeutet die Verwendung eines einzelnen Rohrs? ' In einem Funktionsargument tun?

82

Nehmen Sie zum Beispiel den folgenden Code:

phpinfo(INFO_MODULES | INFO_ENVIRONMENT | INFO_VARIABLES);

Es wird ein einzelnes Argument verwendet, aber ich stelle eine Liste von Optionen bereit, die durch ein einzelnes Pipe-Symbol getrennt sind.

  • Was genau passiert mit dem Argumentwert in der Funktion?
  • Kann ich dasselbe in meinen eigenen Funktionen verwenden?
  • Ist das so und gibt es Vorteile gegenüber der Übergabe eines Arrays?
kryptisch ツ
quelle
Das ist die bitweise Version von OR, die reguläre Version hätte zwei Pipes.
Adeneo
32
Weißt du, ich kann nicht darüber hinwegkommen, wie einige Kommentatoren die Bereitschaft eines Benutzers, Fragen zu stellen, herabsetzen ... Bis zu dem Punkt, dass ein Benutzer mit 210.000 Wiederholungen benötigt, um diese zu beantworten!
Nickhar
5
Ich frage mich, ob ein Benutzer mit einem Ruf von> 5000 auf SO, der keine Fragen gestellt hat, wirklich keine Fragen hat oder das Stellen von Fragen als Zeichen von Schwäche betrachtet.
Peter
15
Lassen Sie uns auch erkennen, dass Symbole schwer zu suchen sind.
Levi Morrison
9
@nickhar .. und das, um auf dieser Dokumentationsseite zu landen, müsste man zuerst mit dem spezifischen Begriff vertraut sein, was irgendwie der
springende

Antworten:

136

Bitweise Operatoren

Bitweise Operatoren ändern die Bits der beteiligten Werte. Ein bitweises ORODER verknüpft im Grunde jedes Bit des linken und rechten Arguments. Zum Beispiel:

5 | 2

Würde in Bits / Binär übersetzen als:

101 | 10

Was dazu führen würde:

111

Weil:

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

Und als Ganzzahl ist dies die Darstellung von 7, die genau das ist, was Sie erhalten, wenn Sie:

echo 5 | 2;

In den Worten von Eddie Izzard ... Flagge!

Wie Ignacio feststellt, wird dies am häufigsten in PHP (und anderen Sprachen) verwendet, um mehrere Flags zu kombinieren. Jedes Flag wird normalerweise als Konstante definiert, deren Wert normalerweise auf eine Ganzzahl gesetzt wird, die nur ein Bit mit einem anderen Offset darstellt:

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

Wenn Sie ORdiese dann zusammen haben, arbeiten sie jeweils mit ihrem eigenen Bitversatz und werden niemals kollidieren:

FLAG_A | FLAG_C

Wird übersetzt in:

1 | 100

Am Ende schalten Sie sich ein:

101

Welches repräsentiert die ganze Zahl 5.

Dann muss der Code nur noch Folgendes tun (der Code, der auf die verschiedenen gesetzten Flags reagiert) (bitweise 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
}

Letztendlich erleichtert es das Lesen der Dinge durch benannte Konstanten und ist im Allgemeinen optimaler, wenn man sich auf ganzzahlige Werte anstatt auf Zeichenfolgen oder Arrays stützt. Ein weiterer Vorteil der Verwendung von Konstanten besteht darin, dass der Compiler, wenn sie bei der Verwendung jemals falsch eingegeben werden, besser in der Lage ist, eine Warnung zu erkennen und auszulösen. Wenn ein Zeichenfolgenwert verwendet wird, kann er nicht erkennen, dass etwas nicht stimmt.

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.
Pebbl
quelle
5
+1 für den tollen Beitrag. Ich hatte große Probleme, meinen Kopf um all das zu wickeln, aber Ihre Erklärungen und Beispiele haben mir geholfen, es viel einfacher zu verstehen, als wenn ich nur die PHP-Dokumentation gelesen hätte. Vielen Dank.
kryptisch ツ
3
@cryptic keine Sorge - schließlich ist die Suche nach etwas, das Sie nicht benennen können, ziemlich schwierig - jetzt, wenn nur Google Absätze von Erklärungen und Beispielen als Suchbegriff akzeptiert :)
Pebbl
4
Tolle Erklärung und Beispiele! +1
Sablefoste
16

Sie übergeben ein Argument, das das bitweise ODER mehrerer Flags ist . Sie können den Operator überall verwenden.

Ignacio Vazquez-Abrams
quelle
10
Vielen Dank, @Ignacio, dass Sie sich daran erinnert haben, dass nicht jeder bei SO ein Experte für Programmierung ist oder sogar weiß, wo er mit der Dokumentation beginnen soll.
Sablefoste