12

I would like first to convert a number to binary, then invert it bitwise. Like this:

Number is 793 = 1100011001 then convert the binary value into: 0011100110

In JavaScript I can do the following:

var x = 793;
document.write(x.toString(2)); // gives 0011100110

This will give me the binary value of the number. But how do I invert the binary bitwise?

I tried the ~ operator, but not working probably. The output is: -1100011010

1
  • 1
    i guess with 793 ^ -1 you would get the bitwise inverted value of any number, just use the operator ^ with left operand as -1 Commented Apr 15, 2019 at 15:29

6 Answers 6

12

MooGoo's answer is correct.

Here is some information about what is happening.... Lets assume this is a 64 bit integer.

793 = 1100011001
~793 = -794 = 1111111111111111111111111111111111111111111111111111110011100110
0x3ff = 1111111111
(-793 & 0x3ff) = 11100110

So you could do this to solve for all cases with this code:

var x = 793; // input value
var y = x.toString(2);
var yl = y.length;
var mask = (Math.pow(2,yl)-1); // calculate mask
var result = ~x & mask;
document.write(result.toString(2)+"<br/>");
Sign up to request clarification or add additional context in comments.

1 Comment

it wouldn't matter, if i remember correctly everything in javascript is 64bit under the covers. the result wether it's 32bit or 64bit will be the same value regardless. I just used 64 bit so i could demonstrate what the negative value really was in binary. Since the "-" doesn't exist in binary, but javascript is trying to be nice when it shows the negative sign on the number. Does that make sense? I'm not that great at explaining it. The difference with the solution i've posted is it's all mathematical. The y and yl piece can be simplified also, i just didn't have the time to get into it
10

You need to use a bitmask.

(~793 & 0x3ff).toString(2) //11100110

Or with XOR

793 ^ 0x3ff

Comments

6

You want to XOR the binary value with 111111111 - however many 1s as there are digits in the original. So:

var x = 793;
var result = x ^ parseInt((new Array(x.toString(2).length+1)).join("1"),2);

(Code for str_repeat taken from PHP.JS)

Revisiting years later, try:

var x = 793;
var result = parseInt(x.toString(2).replace(/[01]/g,function(n) {return 1-n;}),2);

I believe this will be more efficient... probably. Could be completely wrong. Oh well.

2 Comments

You can also register this is a prototype function, if you're going to use it a lot: Number.prototype.negate = function() {return this ^ parseInt((new Array(this.toString(2).length+1)).join("1"),2);}; - This way you can have var x = 793; var c = x.negate();
Good God, all this string munging is not very much in the spirit of bitwise operations is it? You could also do it like 793..toString(2).replace(/1/g, 'a').replace(/0/g, '1').replace(/a/g, '0') but you'd probably cause a 6502 CPU somewhere to melt.
2

Not the shortest code but more readable. My technique is similar to @Ivo Wetzel:

const bitwiseComplement = (N) => {
  let binary = N.toString(2); // 793 is "1100011001" in binary
  binary = binary.split('').map(x => {
    return (x == 1) ? 0 : 1;
  }).join('');
  return binary; // with complement "0011100110" in binary
};

console.log(bitwiseComplement(793));

One-liner javascript solution. Regex /[0-1]/g means match a single character present in the list below [0-1].

const bitwiseComplement = (N) => {
  return N.toString(2).replace(/[0-1]/g, (v) => (v == 1 ? 0 : 1));
};

console.log(bitwiseComplement(793));

Comments

0

I just do this

Let's say x = -11.3 and it's a 16 bit integer from somewhere.

My results will go into variable r.

var r = ((x & 0x7FFF) ^ 0x7FFF)+1;

It's the kiss principle.

2 Comments

How is -11.3 an integer?
& 0x7FFF is redundant
-1

Update

It's unclear to me whether you want a string of the inverted value, if so you can do this:

function invert(x){
    var e = x.toString(2).split('');
    for(var i = 0, l = e.length; i < l; i++) {
        e[i] = e[i] === '0' ? '1' : (e[i] === '1' ? '0' : e[i]);
    }
    return e.join('');
}
invert(793); // '0011100110'
invert(-793); // '-0011100110'

This will also preserve leading zeros.

4 Comments

I don't understand how this answers the question, because xoring with 0 does not change any bits, as you demonstrated.
@Greg Ah, brain lag sorry copied the wrong stuff from my shell, gonna fix it
xor'ing an element with 0 does nothing
Sorry, lacking sleep :/ Updated the answer.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.