2015-04-12 89 views
-1

如何將"0000000f"這樣的字符串解析爲unsigned long long int?而對於較大的值,我該如何解析一個字符串,如"0000000f,0000000f"分別表示高位和低位32位?將十六進制字符串表示法解析爲整數

P.S.在這個問題中不能使用庫函數。

+1

出了什麼問題解析'0000000F,0000000f'作爲兩個不同的unsigned long類型的多頭和32個後左bitshifts到第一在一起或運算呢? – holgac

+1

'unsigned long long x = strtoull(「0000000f」,NULL,16);' –

+0

我不能在這個問題上真的使用stdlib函數 – Soho

回答

0

下面是使用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(); 
} 
+0

[Demo](http://ideone.com/7XhiGs) –

+0

我很欣賞這個我應該在原文中提到它:不能依賴庫函數。 – Soho

+0

第二次調用scanf將失敗,因爲輸入流指針已經超過了數據。建議保存第一個scanf的返回值。那麼如果返回值爲1,則處理單個輸入值,否則如果輸入值爲2,則處理雙輸入值,否則處理輸入失敗 – user3629249

1

您可以使用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; 
} 

您可以選擇忽略空格和其他字符或停止解析和我一樣。

+0

這一行:'unsigned long v1'應該是:'unsigned long long v1';' – user3629249

+0

@ user3629249:當然!我修好了它。 – chqrlie

1

像@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; 
} 
相關問題