Pourquoi préférer le complément de deux au signe-et-magnitude pour les numéros signés?

je suis juste curieux s'il y a une raison pour laquelle afin de représenter -1 en binaire, le complément de two est utilisé: retourner les bits et ajouter 1?

-1 est représenté par 11111111 (le complément de two) plutôt que (pour moi plus intuitif) 10000001 qui est binaire 1 avec le premier bit comme drapeau négatif.

avertissement: Je ne compte pas sur l'arithmétique binaire pour mon travail!

167
demandé sur Deduplicator 2009-07-14 17:15:08

18 réponses

il est fait de sorte que l'addition n'a pas besoin d'avoir une logique spéciale pour traiter les nombres négatifs. Voir l'article sur Wikipedia .

dites que vous avez deux numéros, 2 et -1. Dans votre façon "intuitive "de représenter les nombres, ils seraient 0010 et 1001 , respectivement (Je m'en tiens à 4 bits pour la taille). À titre de complément, ils sont 0010 et 1111 . Maintenant, disons que je veux ajouter.

l'ajout de complément de Two est très simple. Vous ajoutez des nombres normalement et tout bit de portage à la fin est éliminé. Ils sont donc ajoutés comme suit:

  0010
+ 1111
=10001
= 0001 (discard the carry)

0001 est 1, qui est le résultat attendu de "2+(-1)".

mais dans votre méthode "intuitive", ajouter est plus compliqué:

  0010
+ 1001
= 1011

qui est -3, c'est ça? Plus Simple ne fonctionne pas dans ce cas. Vous avez besoin de noter que l'un des nombres est négatif et l'utilisation d'un algorithme différent si c'est le cas.

pour cette méthode de stockage" intuitive", la soustraction est une opération différente de l'addition, nécessitant des contrôles supplémentaires sur les nombres avant qu'ils puissent être ajoutés. Puisque vous voulez que les opérations les plus basiques (addition, soustraction, etc) soient aussi rapides que possible, vous devez stocker les nombres d'une manière qui vous permet d'utiliser les algorithmes les plus simples possibles.

en outre, en la méthode de stockage" intuitive", il y a deux zéros:

0000  "zero"
1000  "negative zero"

qui sont intuitivement le même nombre, mais ont deux valeurs différentes lorsqu'ils sont stockés. Chaque application devra prendre des mesures supplémentaires pour s'assurer que les valeurs non nulles sont pas aussi négatif zéro.

il y a un autre bonus avec le stockage des ints de cette façon, et c'est quand vous avez besoin d'étendre la largeur du registre où la valeur est stockée. Avec le complément de deux, stockant un 4-bit le nombre dans un registre de 8 bits est une question de répéter son bit le plus significatif:

    0001 (one, in four bits)
00000001 (one, in eight bits)
    1110 (negative two, in four bits)
11111110 (negative two, in eight bits)

c'est juste une question de regarder le morceau de signe du mot plus petit et de le répéter jusqu'à ce qu'il rembourse la largeur du mot plus grand.

avec votre méthode, vous devez effacer le bit existant, qui est une opération supplémentaire en plus de rembourrage:

    0001 (one, in four bits)
00000001 (one, in eight bits)
    1010 (negative two, in four bits)
10000010 (negative two, in eight bits)

vous avez encore besoin de mettre ces 4 bits supplémentaires dans les deux cas, mais dans le "intuitive" cas, vous devez effacer la 5ème peu aussi. C'est une petite étape supplémentaire dans l'une des plus fondamentales et les opérations les plus courantes présentes dans chaque application.

285
répondu Welbog 2016-04-07 16:16:09

Wikipedia en dit long:

le système du Double Complément a l'avantage de ne pas exiger que les circuits d'addition et de soustraction examinent les signes des opérandes pour déterminer s'il faut ajouter ou soustraire. Cette propriété rend le système à la fois plus simple à mettre en œuvre et capable de manipuler facilement l'arithmétique de précision supérieure. De plus, Zéro n'a qu'une seule représentation, évitant les subtilités associées à zéro négatif, qui existe dans nos systèmes de complément.

en d'autres termes, l'addition est la même, que le nombre soit négatif ou non.

17
répondu Yacoby 2009-07-14 13:18:27

même si cette question Est ancienne , laissez-moi mettre mes 2 cents.

avant d'expliquer ceci, revenons aux bases. Le complément 2' est le complément 1 ' + 1 . Maintenant quel est le 1er complément et quelle est son importance en plus.

somme de n'importe quel nombre n-bit et son complément 1 vous donne le nombre le plus élevé possible qui peut être représenté par ces N-bits. Exemple:

 0010 (2 in 4 bit system)
+1101 (1's complement of 2)
___________________________
 1111  (the highest number that we can represent by 4 bits)

maintenant que se passera-t-il si nous essayons d'ajouter 1 de plus pour le résultat. Il se traduit par un dépassement de capacité.

le résultat sera 1 0000 qui est 0 (comme nous travaillons avec des nombres de 4 bits, (le 1 à gauche est un débordement )

,

Any n-bit number + its 1's complement = max n-bit number
Any n-bit number + its 1'complement + 1 = 0 ( as explained above, overflow will occur as we are adding 1 to max n-bit number)

Quelqu'un a alors décidé d'appeler le complément 1 + 1 comme complément 2. Si la déclaration ci-dessus devient: N'importe quel nombre de n'bit + son complément de 2 = 0 ce qui signifie que le complément de 2 d'un nombre = - (de ce nombre)

Cela nous amène à une autre question: Pourquoi ne pouvons-nous utiliser que le (n-1) des bits n pour représenter le nombre positif et pourquoi le nième bit le plus à gauche représente le signe (0 sur le bit le plus à gauche signifie +nombre ve , et 1 signifie-nombre ve)? par exemple , pourquoi n'utilisons-nous que les 31 premiers bits d'un int en java pour représenter un nombre positif si le 32ème bit est 1, son numéro a-ve.

 1100 (lets assume 12 in 4 bit system)
+0100(2's complement of 12)
___________________________

1 0000 (résultat zéro , avec le report 1 débordant)

ainsi le système of (N + 2'complément of n) = 0 , fonctionne toujours. La seule ambiguïté ici est le complément 2 de 12 est 0100 qui représente aussi de façon ambiguë +8, autre que la représentation -12 dans le système de complément 2s.

ce problème sera résolu si les nombres positifs ont toujours un 0 dans leur gauche Plus bit. Dans ce cas , le complément de leurs 2 aura toujours un 1 dans leur bit le plus à gauche, et nous n'aurons pas l'ambiguïté du même ensemble de bits représentant le nombre de complément d'un 2 ainsi qu'un + ve nombre.

11
répondu Rpant 2014-06-14 14:49:00

complément de deux permet l'addition et la soustraction à faire de la manière normale (comme vous blessure pour les nombres non signés). Il empêche également -0 (une façon séparée de représenter 0 qui ne serait pas égale à 0 avec la méthode normale bit-by-bit de comparer des nombres).

8
répondu Zifre 2009-07-14 13:17:22

il s'agit de simplifier les sommes et les différences de nombres. une somme d'un nombre négatif et un positif, codifiée par 2 complète est la même qu'en faisant la somme dans la voie normale.

6
répondu Stefano Verna 2009-07-14 13:17:57

la mise en œuvre habituelle de l'opération est de" retourner les bits et ajouter 1", mais il y a une autre façon de la définir qui rend probablement la logique plus claire. Le complément de 2 est la forme que vous obtenez si vous prenez la représentation habituelle non signée où chaque bit contrôle la puissance suivante de 2, et juste faire le terme le plus significatif négatif.

en Prenant une valeur de 8 bits d'un 7 un 6 un 5 un 4 un 3 un 2 un 1 un 0

l'interprétation binaire non signée habituelle est:

2 7 * 7 + 2 6 *un 6 + 2 5 *un 5 + 2 4 *un 4 + 2 3 * 3 + 2 2 *un 2 + 2 1 *un 1 + 2 0 *un 0

11111111 = 128 + 64 + 32 + 16 + 8 + 4 + 2 + 1 = 255

l'interprétation du complément des deux est:

-2 7 * 7 + 2 6 *un 6 + 2 5 *un 5 + 2 4 *un 4 + 2 3 *un 3 + 2 2 *un 2 + 2 1 *un 1 + 2 0 *un 0

11111111 = -128 + 64 + 32 + 16 + 8 + 4 + 2 + 1 = -1

aucun des autres bits ne change de sens du tout, et de porter dans un 7 est "débordement" et ne devrait pas fonctionner, donc à peu près tous les opérations arithmétiques fonctionnent sans modification (comme d'autres l'ont noté). Signe-magnitude généralement inspecter le bit de signe et d'utiliser une logique différente.

5
répondu puetzk 2017-01-19 19:58:34

, Pour s'étendre sur les autres réponses:

en complément de two

  • L'addition est le même mécanisme que l'addition d'entiers positifs simples.
  • soustraire ne change pas trop
  • la Multiplication aussi!

la Division nécessite un mécanisme différent.

tout cela est vrai parce que le complément de two est juste arithmétique modulaire normale, où nous choisir de regarder quelques chiffres négatifs en soustrayant le modulo.

4
répondu yairchu 2009-07-14 13:27:57
Le complément de

Two permet d'additionner des nombres négatifs et positifs sans aucune logique particulière.

si vous avez essayé d'ajouter 1 et -1 en utilisant votre méthode

10000001 (-1)

+00000001 (1)

vous obtenez

10000010 (-2)

au lieu de cela, en utilisant le complément de two, nous pouvons ajouter

11111111 (-1)

+00000001 (1) vous obtenez

00000000 (0)

il en est de même pour la soustraction.

Aussi, si vous essayez de soustraire 4 de 6 (deux nombres positifs), vous pouvez complément de 2 4 et ajouter les deux ensemble 6 + (-4) = 6 - 4 = 2

cela signifie que la soustraction et l'addition de nombres positifs et négatifs peuvent tous être faites par le même circuit dans le cpu.

3
répondu CodeFusionMobile 2009-07-14 13:24:22

en lisant les réponses à cette question, je suis tombé sur ce commentaire [édité].

L'effectif de

2 de 0100 (4) sera de 1100. 1100, c'est 12 si je dis normalement. Si, quand je dis 1100 normal alors il est 12, mais quand je dis 2 complément 1100 alors il est de -4? Aussi, en Java quand 1100 (supposons 4 bits pour le moment) est stocké alors comment déterminer si elle est +12 ou -4 ?? – hagrawal Jul 2 à 16: 53

dans mon la question posée dans ce commentaire est assez intéressante et j'aimerais donc d'abord la reformuler et ensuite donner une réponse et un exemple.

QUESTION-comment le système peut-il établir comment un ou plusieurs octets adjacents doivent être interprétés? En particulier, comment le système peut-il établir si une séquence donnée d'octets est un nombre binaire simple ou un nombre complémentaire de 2?

réponse – le système établit comment interpréter une séquence d'octets à travers les types. Types définis

  • combien d'octets doivent être considérés
  • comment ces octets doivent être interprétés

exemple – ci-dessous nous supposons que

  • char '1519400920"
  • short 's sont les 2 octets
  • int et float , ce sont 4 octets de long

veuillez noter que ces tailles sont spécifiques à mon système. Bien qu'assez commun, ils peuvent être différents d'un système à l'autre. Si vous êtes curieux de ce qu'ils sont sur votre système, utilisez la opérateur sizeof .

tout d'Abord, nous définissons un tableau contenant 4 octets et initialiser tous pour le nombre binaire 10111101 , correspondant au nombre hexadécimal BD .

// BD(hexadecimal) = 10111101 (binary)
unsigned char   l_Just4Bytes[ 4 ]   =   { 0xBD, 0xBD, 0xBD, 0xBD };

Ensuite, nous lisons le contenu du tableau en utilisant différents types.

unsigned char et signed char

// 10111101 as a PLAIN BINARY number equals 189
printf( "l_Just4Bytes as unsigned char  -> %hi\n", *( ( unsigned char* )l_Just4Bytes ) );

// 10111101 as a 2'S COMPLEMENT number equals -67
printf( "l_Just4Bytes as signed char    -> %i\n", *( ( signed char* )l_Just4Bytes ) );

unsigned short et short

// 1011110110111101 as a PLAIN BINARY number equals 48573
printf( "l_Just4Bytes as unsigned short -> %hu\n", *( ( unsigned short* )l_Just4Bytes ) );

// 1011110110111101 as a 2'S COMPLEMENT number equals -16963
printf( "l_Just4Bytes as short          -> %hi\n", *( ( short* )l_Just4Bytes ) );

unsigned int , int et float

// 10111101101111011011110110111101 as a PLAIN BINARY number equals 3183328701
printf( "l_Just4Bytes as unsigned int   -> %u\n", *( ( unsigned int* )l_Just4Bytes ) );

// 10111101101111011011110110111101 as a 2'S COMPLEMENT number equals -1111638595
printf( "l_Just4Bytes as int            -> %i\n", *( ( int* )l_Just4Bytes ) );

// 10111101101111011011110110111101 as a IEEE 754 SINGLE-PRECISION number equals -0.092647
printf( "l_Just4Bytes as float          -> %f\n", *( ( float* )l_Just4Bytes ) );

les 4 octets de la RAM ( l_Just4Bytes[ 0..3 ] ) restent toujours exactement les mêmes. La seule chose qui change, c'est la façon dont nous les interprétons.

encore, nous dites-le système comment interpréter par types .

par exemple, ci-dessus nous avons utilisé les types suivants pour interpréter le contenu du l_Just4Bytes tableau

  • unsigned char : 1 octet dans la plaine binaire
  • signed char : 1 octet en complément de 2
  • unsigned short : 2 octets en binaire simple notation
  • short : 2 octets dans le complément de 2
  • unsigned int : 4 octets en notation binaire simple
  • int : 4 octets dans le complément de 2
  • float : 4 octets in IEEE 754 single-precision notation

[modifier] ce message a été modifié après le commentaire de user4581301. Merci d'avoir pris le temps de déposer ces quelques utile lignes de!

2
répondu mw215 2015-09-06 22:17:43

vous pouvez regarder le professeur Jerry Cain de Stanford expliquant le complément des deux, dans la deuxième conférence (l'explication concernant le complément des deux commence vers 13h00) dans la série de conférences appelées paradigmes de programmation disponibles à regarder sur la chaîne YouTube de Standford. Voici le lien vers la série de conférences: http://www.youtube.com/view_play_list?p=9D558D49CA734A02 .

1
répondu alexs 2009-07-15 07:15:04

le complément de Two est utilisé parce qu'il est plus simple à mettre en œuvre dans les circuits et ne permet pas non plus un zéro négatif.

S'il y a x bits, le complément de two va de +(2^x/2+1) à -(2^x/2). Le complément d'une personne va de +(2^x/2) à -(2^x/2), mais permet un zéro négatif (0000 est égal à 1000 dans un système de complément 4 bit 1).

0
répondu samoz 2009-07-14 13:21:21

Eh bien, votre intention n'est pas vraiment d'inverser tous les bits de votre nombre binaire. Il s'agit en fait de soustraire chacun de ses chiffres de 1. C'est juste une coïncidence heureuse que soustraire 1 de 1 donne 0 et soustraire 0 de 1 donne 1. Donc retourner des bits est effectivement effectuer cette soustraction.

mais pourquoi trouvez-vous la différence de chaque chiffre de 1? Eh bien, vous n'êtes pas. Votre intention réelle est de calculer la différence du nombre binaire donné d'un autre nombre binaire qui a le même nombre de chiffres, mais ne contient que 1. Par exemple, si votre numéro est 10110001, lorsque vous retournez tous ces bits, vous calculez effectivement (11111111 - 10110001).

cela explique la première étape dans le calcul du complément de Two. Maintenant, incluons la deuxième étape -- ajouter 1 -- aussi dans l'image.

ajouter 1 à l'équation binaire ci-dessus:

11111111 - 10110001 + 1

qu'est-ce que tu obtiens? Ceci:

100000000-10110001

C'est l'équation finale. Et en effectuant ces deux étapes vous essayez de trouver cette, dernière différence: le nombre binaire soustrait d'un autre nombre binaire avec un chiffre supplémentaire et contenant des zéros sauf à la position la plus significative bit.

mais pourquoi voulons-nous vraiment cette différence? Ainsi, à partir de là, je suppose que ce serait mieux si vous avez lu L'article de Wikipedia .

0
répondu Frederick The Fool 2009-07-14 13:40:48

nous effectuons seulement l'opération d'addition pour l'addition et la soustraction. Nous ajoutons le second opérande au premier opérande pour ajout. Pour soustraire, nous ajoutons le complément 2 du second opérande au premier opérande.

avec une représentation de complément 2 nous n'avons pas besoin de composants numériques séparés pour la soustraction-seuls les adders et les complementers sont utilisés.

0
répondu subhakar 2012-03-01 20:01:33

il est intéressant de noter que sur certaines machines à additionner anciennes, avant les jours des ordinateurs numériques, soustraction serait effectuée en ayant l'opérateur entrer des valeurs en utilisant un ensemble de couleurs différentes légendes sur chaque clé (de sorte que chaque clé entrerait neuf moins le nombre à être soustrait), et appuyez sur un bouton spécial supposerait un carry dans un calcul. Ainsi, sur une machine à six chiffres, pour soustraire 1234 d'une valeur, l'opérateur frapperait des touches qui indiqueraient normalement "998,765" et appuyez sur un bouton pour ajouter cette valeur plus un au calcul en cours. En complément à deux arithmétique est tout simplement l'équivalent binaire de cette "dix-complément" de l'arithmétique.

0
répondu supercat 2012-11-16 21:57:48

l'avantage d'effectuer la soustraction par la méthode du complément est la réduction du matériel

complexité.Les différents circuits numériques ne sont pas nécessaires pour l'addition et la soustraction.les deux l'addition et la soustraction sont réalisées par l'additionneur.

0
répondu user2640494 2013-08-01 03:52:06

un avantage majeur de la représentation du complément de deux qui n'a pas encore été mentionné ici est que les bits inférieurs de la somme, de la différence ou du produit du complément de deux dépendent seulement des bits correspondants des opérandes. La raison pour laquelle la valeur signée de 8 bits pour -1 est 11111111 est que la soustraction de tout entier dont les 8 bits les plus bas sont 00000001 de tout autre entier dont les 8 bits les plus bas sont 0000000 donnera un entier dont les 8 bits les plus bas sont 11111111 . Mathématiquement, la valeur -1 serait une chaîne infinie de 1's, mais toutes les valeurs comprises dans la plage d'un type entier particulier seront soit toutes les 1's ou toutes les 0's au-delà d'un certain point, il est donc pratique pour les ordinateurs de "signer-étendre" le bit le plus significatif d'un nombre comme s'il représentait un nombre infini de 1's ou 0's.

complément à Deux est à peu près le seul signés-nombre de représentation qui fonctionne bien quand traiter avec des types plus grands que la taille de mot naturelle d'une machine binaire, car lors de l'exécution de l'addition ou de la soustraction, le code peut aller chercher le morceau le plus bas de chaque opérande, calculer le morceau le plus bas du résultat, et stocker cela, puis Charger le morceau suivant de chaque opérande, calculer le morceau suivant du résultat, et stocker cela, etc. Ainsi, même un processeur qui nécessite toutes les additions et soustractions pour passer par un seul registre de 8 bits peut traiter des nombres signés de 32 bits de manière raisonnablement efficace (plus lente que avec un registre de 32 bits, bien sûr, mais encore réalisable).

lors de l'utilisation de toutes les autres représentations signées autorisées par la norme C, chaque bit du résultat pourrait être affecté par n'importe quel bit des opérandes, ce qui rend nécessaire de tenir une valeur entière dans les registres à la fois ou bien suivre des calculs avec une étape supplémentaire qui, dans au moins quelques cas, nécessiterait la lecture, la modification et la réécriture de chaque morceau du résultat.

0
répondu supercat 2016-12-28 15:16:59

parce que les fabricants de CPU sont paresseux!

0
répondu mehrdad 2018-09-05 01:15:13

une réponse satisfaisante à la question de savoir pourquoi le complément de Two2 est utilisé pour représenter des nombres négatifs plutôt que son propre système de complément est que Le système de complément de Two résout le problème de représentations multiples de 0 et le besoin de end-around-carry qui existent dans le système de complément de One de représenter des nombres négatifs.

pour plus D'information, visitez https://en.wikipedia.org/wiki/Signed_number_representations

pour une visite en fin de journée https://en.wikipedia.org/wiki/End-around_carry

-1
répondu Harshit Bhatia 2016-07-21 18:18:30