简体   繁体   English

C库函数,用于将十六进制数字字符串转换为整数吗?

[英]C Library function for converting a string of hex digits to ints?

I have a variable length string where each character represents a hex digit. 我有一个可变长度的字符串,其中每个字符代表一个十六进制数字。 I could iterate through the characters and use a case statement to convert it to hex but I feel like there has to be a standard library function that will handle this. 我可以遍历字符并使用case语句将其转换为十六进制,但是我觉得必须有一个标准的库函数来处理这个问题。 Is there any such thing? 有这样的事吗?

Example of what I want to do. 我想做的事的例子。 "17bf59c" -> int intarray[7] = { 1, 7, 0xb, 0xf, 5, 9, 0xc} "17bf59c" -> int intarray[7] = { 1, 7, 0xb, 0xf, 5, 9, 0xc}

No, there's no such function, probably because (and now I'm guessing, I'm not a C standard library architect by a long stretch) it's something that's quite easy to put together from existing functions. 不,没有这样的功能,可能是因为(现在我猜,我不是很长时间的C标准库设计师),这很容易与现有功能组合在一起。 Here's one way of doing it decently: 这是一种体面的方式:

int * string_to_int_array(const char *string, size_t length)
{
  int *out = malloc(length * sizeof *out);
  if(out != NULL)
  {
    size_t i;
    for(i = 0; i < length; i++)
    {
      const char here = tolower(string[i]);
      out[i] = (here <= '9') ? (here - '\0') : (10 + (here - 'a'));
    }
  }
  return out;
}

Note: the above is untested. 注意:以上未经测试。

Also note things that maybe aren't obvious, but still subtly important (in my opinion): 还要注意一些可能不明显但仍然很重要的事情(在我看来):

  1. Use const for pointer arguments that are treated as "read only" by the function. const用于该函数视为“只读”的指针参数。
  2. Don't repeat the type that out is pointing at, use sizeof *out . 不要重复out指向的类型,请使用sizeof *out
  3. Don't cast the return value of malloc() in C. 不要在C中malloc()的返回值。
  4. Check that malloc() succeeded before using the memory. 在使用内存之前,请检查malloc()成功。
  5. Don't hard-code ASCII values, use character constants. 不要硬编码ASCII值,请使用字符常量。
  6. The above still assumes an encoding where 'a'..'f' are contigous, and would likely break on eg EBCDIC . 上面仍然假设编码是'a'..'f'连续的,并且可能会在EBCDIC上中断。 You get what you pay for, sometimes. 您有时会得到所要支付的费用。 :) :)

using strtol 使用strtol

void to_int_array (int *dst, const char *hexs)
{
    char buf[2] = {0};
    char c;
    while ((c = *hexs++)) {
        buf[0] = c;
        *dst++ = strtol(buf,NULL,16);
    }
}

Here's another version that allows you to pass in the output array. 这是另一个允许您传递输出数组的版本。 Most of the time, you don't need to malloc, and that's expensive. 大多数时候,您不需要malloc,这很昂贵。 A stack variable is typically fine, and you know the output is never going to be bigger than your input. 堆栈变量通常很好,并且您知道输出永远不会比输入大。 You can still pass in an allocated array, if it's too big, or you need to pass it back up. 如果太大,仍然可以传递分配的数组,或者需要将其备份。

#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>

/* str of length len is parsed to individual ints into output
* length of output needs to be at least len.
* returns number of parsed elements. Maybe shorter if there
* are invalid characters in str.
*/
int string_to_array(const char *str, int *output)
{
    int *out = output;
    for (; *str; str++) {
        if (isxdigit(*str & 0xff)) {
            char ch = tolower(*str & 0xff);
            *out++ = (ch >= 'a' && ch <= 'z') ? ch - 'a' + 10 : ch - '0';
        }
    }
    return out - output;
}

int main(void)
{
    int values[10];
    int len = string_to_array("17bzzf59c", values);
    int i = 0;
    for (i = 0; i < len; i++) 
        printf("%x ", values[i]);
    printf("\n");
    return EXIT_SUCCESS;
}
#include <stdio.h>

int main(){
    char data[] =  "17bf59c";
    const int len = sizeof(data)/sizeof(char)-1;
    int i,value[sizeof(data)/sizeof(char)-1];

    for(i=0;i<len;++i)
        sscanf(data+i, "%1x",value + i);

    for(i=0;i<len;++i)
        printf("0x%x\n", value[i]);
    return 0;
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM