Bitwise Operations in PHP

Bitwise operations in PHP?

You could use it for bitmasks to encode combinations of things. Basically, it works by giving each bit a meaning, so if you have 00000000, each bit represents something, in addition to being a single decimal number as well. Let's say I have some preferences for users I want to store, but my database is very limited in terms of storage. I could simply store the decimal number and derive from this, which preferences are selected, e.g. 9 is 2^3 + 2^0 is 00001001, so the user has preference 1 and preference 4.

 00000000 Meaning       Bin Dec    | Examples
│││││││└ Preference 1 2^0 1 | Pref 1+2 is Dec 3 is 00000011
││││││└─ Preference 2 2^1 2 | Pref 1+8 is Dec 129 is 10000001
│││││└── Preference 3 2^2 4 | Pref 3,4+6 is Dec 44 is 00101100
││││└─── Preference 4 2^3 8 | all Prefs is Dec 255 is 11111111
│││└──── Preference 5 2^4 16 |
││└───── Preference 6 2^5 32 | etc ...
│└────── Preference 7 2^6 64 |
└─────── Preference 8 2^7 128 |

Further reading

  • http://www.weberdev.com/get_example-3809.html
  • http://stu.mp/2004/06/a-quick-bitmask-howto-for-programmers.html
  • Why should I use bitwise/bitmask in PHP?
  • http://en.wikipedia.org/wiki/Mask_%28computing%29

How To Test PHP Bitwise Function Input Parameters

I think you'll find that flags like this are normally defined as powers of 2, e.g.:

define('FLAGA',1);
define('FLAGB',2);
define('FLAGC',4); /* then 8, 16, 32, etc... */

As you rightly stated, these can be combined by using a bitwise OR operator:

foo('test.txt',FLAGA | FLAGB | FLAGC);

To test these flags inside your function, you need to use a bitwise AND operator as follows:

function foo($sFile, $vFlags) {
if ($vFlags & FLAGA) {
// FLAGA was set
}
if ($vFlags & FLAGB) {
// FLAGB was set
}
//// etc...
}

bitwise operator in PHP

In bits:

  1. 01
  2. 10
  3. 11

The & operator returns all bits set to 1 in both numbers. So:

  • 1 & 2 -> 01 & 10 -> 00 == 0
  • 2 & 3 -> 10 & 11 -> 10 == 2

Bitwise operations on boolean values

Answer 1

Parts of a boolean expressions (||, &&, !, ...) are only evaluated if needed (from left to right):

  if ($a | func()) { } // func is always called
if ($a || func()) { } // func is not called if $a is true,
// because expression is true whatever func will return
if ($a && func()) { } // func is not called if $a is false,
// because expression is false whatever func will return
func() || exit(); // exit() will be called if func() returns false

Take a look at the documentation: http://php.net/manual/en/language.operators.logical.php

Answer 2

~true seems not to be meaningful: true is 0x00...01 and ~true will be 0xff...fe and not false 0x000...0:

var_dump(~((int)true)); // prints: int(-2)
echo dechex(~((int)true)); // prints: fffffffffffffffe

Use !-operator instead:

var_dump(!true); // prints: bool(false)

Résumé

Use bitwise operators only if you need to change bits.

Bitwise OR operator in PHP, Bug or Feature?

That's due to the bitwise OR operator. It interprets each string as binary and performs the operation.

01101000 // 'h'
00101111 // '/'
-- OR --
01101111 // 'o'

^ looking at the first character

Further Explanation

PHP seems to loop through each character of a string and apply the bitwise operator to it.

So what actually happens is more like:

"h" | "/" -> "o"
"t" | "" -> "t"
"t" | "" -> "t"
"p" | "" -> "p"
...

Any empty string in bitwise operations would end up being all 0s in binary, so if we just look at the first two characters for comparison

// character at index [0]
"h" -> 01101000 (104)
"/" -> 00101111 (47)
-- OR --
"o" -> 01101111 (111)

// character at index [1]
"t" -> 01110100 (116)
"" -> 00000000 (0)
-- OR --
"t" -> 01110100 (116)

How bitwise operator works

Odd numbers in binary always have a least-significant bit (LSB) of 1. That is why your code

function odd($var){
return ($var & 1);
}

returns true on odd numbers. Here are your examples from your question:

(decimal) 4 & 1 = (binary) 100 & 001 = (binary) 000 = (decimal) 0 = false
(decimal) 5 & 1 = (binary) 101 & 001 = (binary) 001 = (decimal) 1 = true

Another way to think of it is

    100 (decimal 4) - an even number 
AND 001 (decimal 1)
= 000 (decimal 0) - return false

and

    101 (decimal 5) - an odd number  
AND 001 (decimal 1)
= 001 (decimal 1) - return true

C & PHP: Storing settings in an integer using bitwise operators?

You sure can do it in PHP.

Let's say you have four booleans you want to store in a single value. That means we need four bits of storage space

0000

Each bit, when set individually, has a unique representation in decimal

0001 = 1 // or 2^0
0010 = 2 // or 2^1
0100 = 4 // or 2^2
1000 = 8 // or 2^3

A common way to implement this is with bit masks to represent each option. PHP's error levels are done this way, for example.

define( 'OPT_1', 1 );
define( 'OPT_2', 2 );
define( 'OPT_3', 4 );
define( 'OPT_4', 8 );

Then when you have an integer that represents 0 or more of these flags, you check with with the bitwise and operator which is &

$options = bindec( '0101' );
// can also be set like this
// $options = OPT_1 | OPT_3;

if ( $options & OPT_3 )
{
// option 3 is enabled
}

This operator works as such: only bits that are set in both operands are set in the result

0101 // our options
0100 // the value of OPT_3
----
0100 // The decimal integer 4 evaluates as "true" in an expression

If we checked it against OPT_2, then the result would look like this

0101 // our options
0010 // the value of OPT_2
----
0000 // The decimal integer 0 evaluates as "false" in an expression

When should I use a bitwise operator?

Bitwise | and & and logical || and && are totally different.

Bitwise operators perform operations on the bits of two numbers and return the result. That means it's not a yes or no thing. If they're being used in conditional statements, they're often used as part of logical comparisons. For example:

if ($x & 2 == 2) {
// The 2^1 bit is set in the number $x
}

Logical operators compare two (or more) conditions/expressions and return true or false. You use them most commonly in conditional statements, like if and while. For example:

if ($either_this || $or_this) {
// Either expression was true
}

How to use the PHP bitwise AND operator with Javascript

Well thanks to the comments of those who responded, and looking and entering the topic, I reviewed the documentation of both languages and then what I did was divide the strings, and do the and - & to each pair of their position and the result it was similar to php.

here as I did.

const a = '100110100011111000100110';
const b = '111111111111111111111110';

function andBin (one, two) {
const _a = one.split('')
const _b = two.split('')
let result = ''

_a.map((e, i) => {
result += Number(e) & Number(_b[i])
})

return result

}

andBin(a, b) // 100110100011111000100110

ready. resolved, thank you all very much.



Related Topics



Leave a reply



Submit