Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/jquery-ui/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
在C语言中将单个字符(十六进制数)转换为整数_C_Integer_Hex_Character - Fatal编程技术网

在C语言中将单个字符(十六进制数)转换为整数

在C语言中将单个字符(十六进制数)转换为整数,c,integer,hex,character,C,Integer,Hex,Character,因此,对于一个赋值,我必须将一个字符(0-F)转换成一个整数(0-15),0-9效果很好,但如果给出任何字母,它会打印一个随机数:例如,对于C,它给出19,对于D则返回20 这是我的方法: int char2int(char digit) { int i = 0; if (digit == 0 || 1 || 2 || 3 || 4 || 5 || 6 || 7 || 8 || 9) i = digit - '0'; else if (digit

因此,对于一个赋值,我必须将一个字符(
0
-
F
)转换成一个整数(
0
-
15
),
0
-
9
效果很好,但如果给出任何字母,它会打印一个随机数:例如,对于
C
,它给出
19
,对于
D
则返回
20

这是我的方法:

int char2int(char digit) {
    int i = 0;

    if (digit == 0 || 1 || 2 || 3 || 4 || 5 || 6 || 7 || 8 || 9)
        i = digit - '0';
    else
    if (digit == 'A' || 'B' || 'C' || 'D' || 'E' || 'F')
        i = digit - '9';
    else
        i = -1;

    return i;
}
起初,我的if语句是这样的:

if (digit => 0 && =< 9)

if (digit => A && =< F)
int char2int(char d) {
    if (d >= '0' && d <= '9') {
        return d - '0';
        }
    d = tolower(d);
    if (d >= 'a' && d <= 'f') {
        return (d - 'a') + 10;
        }
    return -1;
    }
if(数字=>0&&=<9)
如果(数字=>A&&=

但这也带来了一些错误。你可以看出我对C不太了解。我当前的If语句有效,但我确信它太长了。

开始时,您走的路是正确的,但有点偏离了方向。试试这个

#include <ctype.h>
int char2int(char d) {
    if (!isxdigit(d)) {
        return -1;
        }
    if (isdigit(d)) {
        return d - '0';
        }
    return (tolower(d) - 'a') + 10;
    }
#包括
int char2int(chard){
如果(!isxdigit(d)){
返回-1;
}
if(isdigit(d)){
返回d-‘0’;
}
返回(tolower(d)-‘a’+10;
}
如果您希望采用更接近靶场测试的方法,您可以这样做:

if (digit => 0 && =< 9)

if (digit => A && =< F)
int char2int(char d) {
    if (d >= '0' && d <= '9') {
        return d - '0';
        }
    d = tolower(d);
    if (d >= 'a' && d <= 'f') {
        return (d - 'a') + 10;
        }
    return -1;
    }
int char2int(chard){
如果(d>='0'&&d='a'&&d
如果(数字==0 | | 1 | | 2 | | | 3 | | | 4 | | 5 | | 6 | | 7 | | 8 | 9)

这不是条件表达式在C中的工作方式

您需要将
数字
分别与每个数字进行比较

if (digit == '0' || digit == '1' || digit == '2' ...
或者用聪明的方法:

if(digit >= '0' && digit <= '9')
                         ^^ not =<

if(digit>='0'&&digit返回值不是随机的。内存中的每个ascii字符都由一个值表示。每个ascii字符的值都可以在

其他响应告诉您条件表达式的错误,但另一个错误是,如果字符是A、B、C、D、E或F,则需要将其转换为int,如
i=(数字-'A')+10
,这意味着取A、B、C、D、E或F的值减去最小值A,然后加上10


此外,您可以看到,如果不需要字符的精确值,可以使用字母连续的属性,而不需要ascii表。

如果您愿意假设字符编码为ascii和2的补码,那么下面的方法非常有效

此代码不是为了可读性。如果有问题,请使用其他解决方案。这是为了严格编码。对于给定的处理器,大约需要10条指令。结果会有所不同

减去1。这将
char
值下移1。特别是,A-Z现在是64-89,A-Z在96-121范围内

测试位(64位)是否清除:在“0”-“9”的范围内。如果是,则增加7并屏蔽以保持该位(64位)清除

否则,屏蔽一个位以将a-z折叠到a-z范围

现在“0”到“9”和“A”到“Z”在一个连续的范围内。只需减去54。除
0-9
之外的所有
unsigned char
值,
A-Z
A-Z
将具有一个大于35的值。这对于以36为基数的任何基本用法都很有用

int Value(char ch) {
  if (!(--ch & 64)) {       // decrement, if ch in the '0' to '9' area ...
    ch = (ch + 7) & (~64);  // move 0-9 next to A-Z codes
  } else {
    ch &= ~32;
  }  
  ch -= 54;                 // -= 'A' - 10 - 1
  if ((unsigned char)ch > 15) { 
    ; // handle error
  }
  return (unsigned char)ch;
}

假设ASCII,以下字符将从字符(0-9,a-f,a-f)转换为关联的无符号整数(0-15)。任何其他字符也将转换为…0-15范围内的某个随机值。垃圾输入,垃圾输出

unsigned hexToUnsigned(char ch) {
    return ((ch | 432) * 239'217'992 & 0xffff'ffff) >> 28;
}
具有32位整数的CPU通常能够消除0xffff'ffff掩蔽。在我的机器上,编译器将此函数转换为:

hexToUnsigned PROC
movsx   eax, cl
or      eax,1B0h
imul    eax, eax, 0E422D48h
shr     eax, 1ch
ret     0
hexToUnsigned ENDP
另一种常见的方法是减少表观操作(只有三个),返回无效字符的总垃圾量(这可能没问题),但也需要除法(这会将其从顶部去掉):

为了说明编译器对除法的感受,他们(至少在x64上)将除法改为倒数的倍数以得到乘积,如果需要余数,再进行一次乘法和减法运算:

hexToUnsigned PROC
; return ((ch | ('A' ^ 'a')) - '0') % 39;
movsx   r8d, cl
mov     eax, -770891565
or      r8d, 32
sub     r8d, 48
imul    r8d
add     edx, r8d
sar     edx, 5
mov     ecx, edx
shr     ecx, 31
add     edx, ecx
imul    ecx, edx, 39
sub     r8d, ecx
mov     eax, r8d
ret     0
hexToUnsigned ENDP
在redis


谢谢!除了d=tolower(d)部分外,这是有意义的。你确定这会返回Int类型吗?我可以做什么:return(digital-'a')+10,以使char F返回15?你应该添加10(我已经将其添加到示例中)你是有意阻止OP学习C吗?@chqrlie,我试图以我(希望还有其他人)的方式回答这个问题——如何将一个十六进制字符转换成整数在搜索后会很高兴找到它。你的一些无聊的解决方案确实很有价值,但对于目前的操作技能水平来说是无法达到的。。。