Char/uchar type overrun summary

We analyzed the value range of char and uchar and the over-limit situation in article one and article two .

to sum up:

1. Char/uchar is essentially a saved integer number, an integer number of one byte; // The so-called character type is actually a character converted from an integer as an ascii code.

2. The value range of char

  • Decimal: 0 to 255
  • Hexadecimal: 0 to FF

3. The value range of uchar

  • Decimal: -128 to 127
  • Hexadecimal: 80 to 7F

4. The char/uchar type exceeds the limit:

Formula: High, minus, plus (plus and minus 256, similar to plus and minus 10 in decimal numbers, namely: plus and minus cycle period)

  • Decimal: When the data is higher than the maximum upper limit, subtract 256; when the data is lower than the minimum lower limit, add 256;

E.g:

    char ch1 = 129;//129-256=-127;

    char ch2 = -130;//-130+256=126;

    uchar ch3=257;//257-256 =1;

    uchar ch4 = -2;//-2+256= 254;
    printf("%d,%d,%d,%d",ch1,ch2,ch3,ch4);

Idea: 32-bit compiler:

Idea 1: 129-----" Complement: 0000 0000 0000 0000 0000 0000 1000 0001---->The 8-bit 1000 0001 after interception, because it is a char type, the highest bit is 1, expanded to %d, sign bit Complement 1, 1111 1111 1111 1111 1111 1111 1000 0001-"

Converted to source code: 1000 0000 0000 0000 0000 0000 0111 1111 ----》-127

Idea 2: 129 = 127+2 ----- "Refer to the figure below, the largest number is 127, and it is -127 when shifted by 2 positions;

Idea 1: -130---"'s complement: 1111 1111 1111 1111 1111 1111 0111 1110-----" After intercepting 8 bits 0111 1110, the highest bit is 0, then use %d (and expand to 4 bytes int) display: 0000 0000 0000 0000 0000 0000 0111 1110---》126

Idea 2: -130= -128-2---"Refer to the figure above, the smallest number, the reverse shift of 2 positions is 126;

Idea 1: 257---" Complement code: 0000 0000 0000 0000 0000 0001 0000 0001----" 8 bits after interception: 0000 0001, because the bit uchar is expanded to %d,0000 0000 0000 0000 0000 0000 0000 0001- --->1

Idea 2: 257=255+2---"Maximum number, 255 moves two positions forward to get 1 (uchar range from 0-255)

Idea 1: -2----->'s complement: 1111 1111 1111 1111 1111 1111 1111 1110------- "8 digits after interception: 1111 1110, because it is uchar, expand to %d, sign bit complement 0, so 254

Idea 2: -2=0-2--------" 2 positions are 254 when moving forward

  • The hexadecimal number of char is out of limit ( see it as a decimal number, char is out of limit, but in fact the hexadecimal number is between 80-7F (1000 0000------0111 1111, which is 256 numbers, including all numbers starting with 0 and starting with 1), not exceeding the limit )
    uchar ch1 = 0xAA;

    char ch2 = 0xAA;

    printf("%d,%d\n%x,%x",ch1,ch2,ch1,ch2);

 

The same hexadecimal number (that is, the binary number 1010 1010), assigning it to uchar type is 170, assigning to char type is -86; no matter what value is assigned, the hexadecimal number itself is unchanged .

ps:

1) We found that there is a difference when printing uchar 0xAA and char 0xAA in hexadecimal format. The reason is:

uchar, 0xAA is a positive number, which is equivalent to 0 in the front, so it is 0xAA;

char, 0xAA (10101010, in fact, this number does not exceed the limit, because the first digit is 1, so it is a negative number, because the integer printed on a 32-bit machine occupies 4 bytes, so it is expanded to 32 bits, and the front is all F ), this is actually a problem of converting the number of short bytes to the number of long bytes.

2) char ch2=0xAA; If printed in %d format, that is, in decimal format, the final value must be converted from hexadecimal to decimal, and then the maximum is calculated according to the method of "high minus low plus".

3) For uchar/char, if it is a one-byte hexadecimal number assignment, how much do we assign and output in hexadecimal (%x, unsigned hexadecimal printing, hexadecimal The system is different from the decimal sign %d/%u, only unsigned.) For char/uchar, if an 8-digit hexadecimal number is assigned, there is no limit violation.

Therefore, we are accustomed to using char/uchar to store hexadecimal numbers, because what you see is what you get.

4) For uchar/char, we assign the value with a one-byte hexadecimal number, and the direct calculation is the source code.

5) The range of uchar is a total of 256 numbers from 0 to 255, and the range of char is a total of 256 numbers from 80 to 7F. Compared with uchar, the range from 80 to FF represents a positive number originally and is now used to represent a negative number.

5. When uchar/char data is a decimal number, the output in hexadecimal form is in complement form. (When uchar/char data is a hexadecimal number, it will be output in hexadecimal format as it is.)

    char ch1 = 129;//129-256=-127;
    char ch2 = -130;//-130+256=126;
    uchar ch3=257;//257-256 =1;
    uchar ch4 = -2;//-2+256= 254;
    printf("%d,%d,%d,%d\n",ch1,ch2,ch3,ch4);
    printf("%x,%x,%x,%x\n",ch1,ch2,ch3,ch4);

    char ch5 = -127;
    char ch6 = 126;
    uchar ch7=1;
    uchar ch8 = 254;
    printf("%d,%d,%d,%d\n",ch5,ch6,ch7,ch8);
    printf("%x,%x,%x,%x\n",ch5,ch6,ch7,ch8);

Summary:

1) Decimal number, output in decimal form, "high minus low plus";

2) Decimal number, output in hexadecimal form, first "high minus low plus", and then converted into one's complement output;

3) Hexadecimal numbers, output in decimal form, converted to decimal numbers, and output "high minus low plus";

4) Hexadecimal number, output in hexadecimal form, output as it is, pay attention to sign complement.

 

 

 

Guess you like

Origin blog.csdn.net/modi000/article/details/113512294