如何将"0000000f"
这样的字符串解析为unsigned long long int
?而对于较大的值,我该如何解析一个字符串,如"0000000f,0000000f"
分别表示高位和低位32位?将十六进制字符串表示法解析为整数
P.S.在这个问题中不能使用库函数。
如何将"0000000f"
这样的字符串解析为unsigned long long int
?而对于较大的值,我该如何解析一个字符串,如"0000000f,0000000f"
分别表示高位和低位32位?将十六进制字符串表示法解析为整数
P.S.在这个问题中不能使用库函数。
下面是使用scanf
一个简单的解决方案:
#include <stdio.h>
#include <stdlib.h>
unsigned long long int parse(char const * s)
{
unsigned long int a, b;
if (sscanf(s, "%8lx,%8lx", &a, &b) == 2)
return ((unsigned long long int) a << 32) + b;
if (sscanf(s, "%8lx", &a) == 1)
return a;
abort();
}
[Demo](http://ideone.com/7XhiGs) –
我很欣赏这个我应该在原文中提到它:不能依赖库函数。 – Soho
第二次调用scanf将失败,因为输入流指针已经超过了数据。建议保存第一个scanf的返回值。那么如果返回值为1,则处理单个输入值,否则如果输入值为2,则处理双输入值,否则处理输入失败 – user3629249
您可以使用strtoull()
从<stdlib.h>
这样:
#include <stdlib.h>
unsigned long long parse_u64(const char *s) {
unsigned long long v1;
v1 = strtoull(s, (char **)&s, 16);
if (*s == ',') {
v1 = (v1 << 32) | strtoull(s + 1, NULL, 16);
}
return v1;
}
注意,没有检测到格式错误。
如果你不能依赖库函数,使用:
int getdigit(int c) {
if (c >= '0' && c <= '9') return c - '0';
if (c >= 'a' && c <= 'f') return c - 'a' + 10;
if (c >= 'A' && c <= 'F') return c - 'A' + 10;
return -1;
}
unsigned long long parse_u64(const char *s) {
unsigned long long v1;
int digit;
for (v1 = 0; *s; s++) {
if (*s == ',')
continue;
digit = getdigit(*s);
if (digit < 0)
break;
v1 = (v1 << 4) | digit;
}
return v1;
}
您可以选择忽略空格和其他字符或停止解析和我一样。
这一行:'unsigned long v1'应该是:'unsigned long long v1';' – user3629249
@ user3629249:当然!我修好了它。 – chqrlie
像@chqrlie,但与其他错误检查,
听起来像是你想有一个字符串整数转换。只要足够:
unsigned chtohex(char ch) {
if (ch >= '0' && ch <= '9') return ch - '0';
if (ch >= 'A' && ch <= 'Z') return ch - 'A' + 10;
if (ch >= 'a' && ch <= 'a') return ch - 'a' + 10;
return (unsigned) -1;
}
// return 0 on success,1 on failure
int my_hexstrtoull(const char *s, unsigned long long *dest) {
unsigned long long sum = 0;
unsigned ch;
while (*s) {
if (*s == ',') continue;
unsigned ch = chtohex(*s++);
if (ch >= 16) {
return 1; // Bad hex char
}
if (sum >= ULLONG_MAX/16) {
return 1; // overflow
}
sum = sum * 16 + ch;
s++;
}
*dest = sum;
return 0;
}
出了什么问题解析'0000000F,0000000f'作为两个不同的unsigned long类型的多头和32个后左bitshifts到第一在一起或运算呢? – holgac
'unsigned long long x = strtoull(“0000000f”,NULL,16);' –
我不能在这个问题上真的使用stdlib函数 – Soho