Benutzer-Werkzeuge

Webseiten-Werkzeuge


php:bitweise

Unterschiede

Hier werden die Unterschiede zwischen zwei Versionen gezeigt.

Link zu dieser Vergleichsansicht

Both sides previous revision Vorhergehende Überarbeitung
Nächste Überarbeitung
Vorhergehende Überarbeitung
php:bitweise [2017/09/30 16:42]
webproducer
php:bitweise [2021/01/05 09:59] (aktuell)
webproducer PHP-Beispiel für die Überprüfung von Öffnungszeiten
Zeile 2: Zeile 2:
  
 Ein praktisches Anwendungsbeispiel für die Nutzung von Bit-Operatoren ist die Speicherung von allen möglichen Kombinationen von Wochentagen in nur einem einzigen Datenbankfeld. Hierfür wird jedem Wochentag ein fester Wert zugeordnet: Ein praktisches Anwendungsbeispiel für die Nutzung von Bit-Operatoren ist die Speicherung von allen möglichen Kombinationen von Wochentagen in nur einem einzigen Datenbankfeld. Hierfür wird jedem Wochentag ein fester Wert zugeordnet:
-^Wochentag^date("​w"​)^Wert^ +^Wochentag^date("​w"​)^Rechenformel^Dezimal-Wert^Binär-Wert^ 
-| Sonntag | 0 | 1 | +| Sonntag | 0 | 2 hoch |1 | 00000001 | 
-| Montag | 1 | 2 | +| Montag | 1 | 2 hoch 1 | 2 | 00000010 ​
-| Dienstag | 2 | 4 | +| Dienstag | 2 | 2 hoch 2 | 4 | 00000100 ​
-| Mittwoch | 3 | 8 | +| Mittwoch | 3 | 2 hoch 3 | 8 | 00001000 ​
-| Donnerstag | 4 | 16 | +| Donnerstag | 4 | 2 hoch 4 | 16 | 00010000 ​
-| Freitag | 5 | 32 | +| Freitag | 5 | 2 hoch 5 | 32 | 00100000 ​
-| Samstag | 6 | 64 | +| Samstag | 6 | 2 hoch 6 | 64 | 01000000 ​|
-| Sonntag | 7| 128 |+
  
-Wenn wir jetzt zB. ein Script nur an den Tagen der Lottoziehung,​ nämlich Mittwoch ​(Wert 8und Samstag (Wert 64), ausführen wollen speichern wir in dem Datenbankfeld den addierten Wert 72.+Für die Erstellung unseres Beispiel sind zunächst nur die Dezimal-Werte interessant. 
 +Der Standardwert für unser Datenbankfeld wäre 127, da dieser Wert alle Wochentage beinhaltetDa wir maximal nur einen Byte zur Darstellung aller möglichen Kombinationen von Wochentagen benötigen reicht ​ein Datenbankfeld vom Typ "​tinyint(3)" aus. Tinyint kann nämlich alle Werte bis genau 127 aufnehmen.
  
-Um festzustellen,​ ob der heutige Tag einem Wochentag des Datenbankfeldes entspricht übersetzen wir das Ergebnis des PHP-Aufrufes date("​w"​) gegen den entsprechenden Werte durch ein Array, wobei wir uns die Angabe des keys sparen, da dieser beim nummerischen Array automatisch von 0 an hochzählt. Als nächstes überprüfen wir, ob unser Wert 72 dem heutigen Wochentag entspricht.+Wenn wir jetzt z. B. ein Script nur an den Tagen der Lottoziehung 6 aus 49, nämlich Mittwoch (Dezimal-Wert 8) und Samstag (Dezimal-Wert 64), ausführen wollen speichern wir in dem Datenbankfeld den addierten Wert 72. 
 + 
 +==== Überprüfung mit PHP ==== 
 + 
 +Um festzustellen,​ ob der heutige Tag einem Wochentag des Datenbankfeldes entspricht übersetzen wir das Ergebnis des PHP-Aufrufes date("​w"​) gegen die entsprechenden ​Dezimal-Werte durch ein Array, wobei wir uns die Angabe des keys sparen, da dieser beim nummerischen Array automatisch von 0 an hochzählt. Als nächstes überprüfen wir, ob unser Wert 72 dem heutigen Wochentag entspricht.
  
 <code php> <code php>
 $weekdays = 72; // Wert aus der Datenbank: Mittwoch und Samstag $weekdays = 72; // Wert aus der Datenbank: Mittwoch und Samstag
  
-$values = array( 1, 2, 4, 8, 16, 32, 64, 128 ); +$today = date( "​w"​ ); // heutiger Wochentag (0 bis 7) 
-$today = date("​w"​ ); // heutiger Wochentag (0 bis 7) +$value = pow( 2, $today ​); // Potzenzwert des heutigen ​Wochentags
-$value = $values[$today]; // heutigen ​Wert aus Wertezuordnung ermitteln+
  
-if( $value & $weekdays )+if( $value & $weekdays ) // wenn der Potzenwert in den Wochtentagen enthalten ist
 { {
     echo "Heute ist Mittwoch oder Samstag!";​     echo "Heute ist Mittwoch oder Samstag!";​
 } }
 </​code>​ </​code>​
 +
 +Der Bit-Operator wird durch die Verwendung eines einfachen kaufmännischen Undzeichens "&"​ gekennzeichnet und gibt als Ergebnis true oder false zurück. Aus diesem Grund müssen UND-Überprüfungen in if-Bedingungen zwingend mit einem doppelten Undzeichen "&&"​ versehen werden.
 +
 +Wenn mehr als die 7 oben angegebenen Potenzwerte benötigt werden können diese auch [[php:​pow|per Funktion]] ermittelt werden. Da ein MySQL-Datenbankfeld vom Typ int (32 Bit) höchstens einen Wert von 2.147.483.647 (2^32) annehmen kann können in diesem Datenbankfeld maximal 31 gleichzeitige Zustände gespeichert werden.
 +Das übrig gebliebene 32. Bit muss für den Fall, dass alle Zustände auf "​aktiv"​ gesetzt werden, reserviert bleiben da die Summe aller 31 Zustände genau dem Wert 2^32 entsprechen.
 +
 +==== PHP-Beispiel für die Überprüfung von Öffnungszeiten ====
 +
 +Mit [[php_isopen|dieser PHP-Funktion "​isOpen"​]] kann anhand von übergebenden Öffnungszeiten überprüft werden, ob z. B. ein Ladengeschäft aktuell geöffnet ist. Hierbei werden für die Angabe von Wochentagen ebenfalls deren Dezimal-Werte verwendet.
 +
 +==== Überprüfung mit mySQL ====
 +
 +Seit der mySQL-Version 5.5 werden Bit-Funktionen und -Operatoren unterstützt. Mit der folgenden SQL-Anweisung können wir alle Spielscheine aus der Datenbank suchen, die an einer Mittwochsziehung teilnehmen. Ausgegeben werden alle Spielscheine,​ die nur an der Mittwochsziehung oder an der Mittwochs- und Samstagsziehung teilnehmen.
 +
 +<code sql>
 +SELECT * FROM spielscheine WHERE (Wochentag & 8) > 0
 +</​code>​
 +
 +
 +===== Technischer Hintergrund =====
 +
 +Die Spalte "​Binär-Wert in der oberen Tabelle soll Aufschluss darüber geben, wie der Bit-Operator intern arbeitet.
 +
 +In unserem Beispiel werden zwei Bits gesetzt: Eins für Mittwoch und eins für Samstag. ​
 +Das Ergebnis ist die Summe der gesetzten Bits.
 +
 +^Wochentag^Bedeutung^Dezimal-Wert^Binär-Wert^
 +| Mittwoch | nur Mittwoch | 8 |00001000 |
 +| Samstag ​ | nur Samstag | 64| 01000000 |
 +| **Ergebnis** | Mittwoch UND Samstag | **72** | **01001000** |
 +
 +Im Umkehrschluss ist nun durch das Ergebnis zu erkennen, welche Wochentage hier gesetzt wurden.
 +Nämlich alle, für die im Ergebnis eine 1 zu sehen ist.
 +
 +==== Performance-Vorteil ====
 +
 +PHP und MySQL ziehen letztlich zum Vergleich ausschließlich den Binär-Wert des Ergebnisses heran um zu überprüfen,​ welche Bits, also in diesem Falle Wochentage, gesetzt wurden. Die Überprüfung eines Wertes durch den Bitweisen Operator ist um ein vielfaches schneller als gleichwertige Vergleiche mit Dezimalzahlen,​ da der Computer standardmäßig mit Binärzahlen arbeitet und diese hierbei nicht erst in Dezimalzahlen umgewandelt werden müssen.
php/bitweise.1506782566.txt.gz · Zuletzt geändert: 2017/09/30 00:00 (Externe Bearbeitung)