2015-09-11 21 views
6

Ich habe den folgenden Code:~ bitweise Operator in JavaScript

var a = parseInt('010001',2); 
console.log(a.toString(2)); 
// 10001 
var b = ~a; 
console.log(b.toString(2)); 
// -10010 

The MSDN Say

~ Führt den NOT-Operator für jedes Bit. NOT a ergibt den invertierten Wert (a.k.a. ein Komplement) von a.

sollte daher zurücks .

This Topic kinda confirm that

So verstehe ich nicht, wie wir -10.010 statt bekommen? Die einzige mögliche Erklärung ist, dass:

010001 101110 negiert wird, aber er diese -10.001 schreiben und dann für einen obskuren Grund, warum er mir die beiden Ergänzungen und -10.001 -10.010 werden.

Aber all dies ist sehr dunkel in meinem Kopf, hätten Sie eine Vorstellung davon, was genau passiert.

+3

Es sieht aus wie Javascript dies ein 32-Bit unterzeichnet hält ich nt unter den Deckeln. 0b010001 = 0x00000011, oder Dezimal 17. Das Einerkomplement von diesem ist 0xFFFFFFEE, oder dezimal -18, wenn es als vorzeichenbehafteter 32-Bit-Int behandelt wird, der 0x11111111111111111111111111,11101110 entspricht. –

+0

Auch 0b10010 ist positiv 18, also -0b10010 ist -18. –

Antwort

2

unter der Decke, wenn Javascript bitweise Operationen der Fall ist, wandelt es in ein 32-Bit-Ganzzahl mit Vorzeichen Darstellung, und verwendet diese, dann das Ergebnis konvertiert zurück in seine interne Dezimaldarstellung.

Als solcher wird Ihr Eingabewert 01000100000000 00000000 00000000 00010001.

Diese wird dann invertiert:

~00000000 00000000 00000000 00010001 => 11111111 11111111 11111111 11101110 

in hex umgestaltet, das der invertierte Wert 0xFFFFFFEE, der dem Dezimalwert von -18 entspricht.

Da dies eine Ganzzahl mit Vorzeichen mit einem Wert von -18, dieser Wert umgewandelt wird, an die darunterliegenden decimal Darstellung von -18 von Javascript.

Wenn Javascript versucht, es als Basis-2-Nummer zu drucken, sieht es das negative Vorzeichen und den Wert von 18, und druckt es als -10010, da 10010 die binäre Darstellung positiver 18.

ist
+0

Danke für deine Antwort Shotgun Ninja. Ich denke, es erklärt, was mich verwirrte ... meine binären Fähigkeiten sind verrostet! :) –

+1

ich füge diesen sehr coolen Link hinzu, um 2's Komplement-Konvertierung zu verstehen http://www.wikihow.com/Convert-a-Negative-Binary-to-Decimal –

0

Gemäß der Dokumentation auf der Mozilla Developer Website here. Bitweis NOT bei jeder Zahl x ergibt - (x + 1). Zum Beispiel ergibt ~ 5 -6. Deshalb erhalten Sie das negative Vorzeichen vor der Nummer.

+0

Nicht sicher, warum die Downvotes als dies das Problem perfekt erklären – musefan

+0

Dies deckt die Details von was tatsächlich passiert, aber es ist eine schöne Faustregel zu erinnern. Wenn das OP bitweise Operationen verwendet, ist es wahrscheinlich korrekter zu erklären, wie sie funktionieren, als es eine Antwort zu liefern, die aus Gründen der Einfachheit über sie glänzt. –

+0

Dies erklärt nicht _Why_, siehe T.J. Crowders Antwort für eine bessere Erklärung. – Nit

3

Die bitweisen Operatoren von JavaScript konvertieren ihre Operanden in 32-Bit-Ganzzahlen mit Vorzeichen (das übliche 2's complement), führen ihre Operation aus und geben das Ergebnis als den am besten geeigneten Wert im JavaScript-Datentyp zurück (Fließkomma mit doppelter Genauigkeit; JavaScript nicht) haben einen Integer-Typ). Mehr in §12.5.11 (Bitwise NOT Operator ~) und §7.1.5 (ToInt32).

So Ihre 10001 ist:

 
00000000 00000000 00000000 00010001 

die, wenn sie ~ ist:

 
11111111 11111111 11111111 11101110 

..., die in der Tat negativ in 2s Darstellung ergänzen.

Sie fragen sich vielleicht: Wenn das Bitmuster wie oben ist, warum hat b.toString(2) Sie -10010 stattdessen geben? Weil es Ihnen eine signierte Binärdatei anzeigt, nicht das tatsächliche Bitmuster. - bedeutet negativ und 10010 bedeutet 18 dezimal. Das Bitmuster oben ist, wie das in 2s Komplementbits dargestellt wird. (Und ja, ich tat zu gehen, um mich überprüfen Sie auf der!)

+0

Aber das ist nicht -18 ist es? – musefan

+1

ist es, sehen, wie Zweierkomplement funktioniert –

+1

@musefan: Stellt sich heraus, ich habe meine Bits nicht falsch. '11111111 11111111 11111111 11101110' in 2s Komplement binär ist -18 dezimal. –

1

uses Javascript 32-Bit-Zahlen mit Vorzeichen, so

a (010001) (17) is 0000 0000 0000 0000 0000 0000 0001 0001 
b = ~a (?) (-18) is 1111 1111 1111 1111 1111 1111 1110 1110 

Der Grund für den Druck -18 als -10010 und Methoden tatsächlichen Wert erhalten erklärt auch hier Link

+0

Danke für die extra Präzision AcidBurn! –