2010-05-18 4 views
2

Я нашел множество различных решений этой проблемы, но не все они работают, и многие из них кажутся несколько хакерскими и неэффективными. В основном у меня есть строка шестнадцатеричных данных (т. Е. «55 AA 41 2A 00 94 55 AA BB BB 00 FF»), которые я хотел бы преобразовать в необработанные данные. Каков наилучший способ сделать это?Преобразование шестнадцатеричной строки в данные

UPDATE: Решение Vicky отлично поработало для меня, но я сменил его на работу с шестнадцатеричными строками, которые не имеют пробелов между ними и немного изменили стиль.

int i = 0; 
char *hexString = "55AA412A009455AABBBB00FF" 
char *hexPtr = hexString; 
unsigned int *result = calloc(strlen(hexString)/2 + 1, sizeof *result); 

while (sscanf(hexPtr, "%02x", &result[i++])) { 
    hexPtr += 2; 
    if (hexPtr >= hexString + strlen(hexString)) break; 
} 

return result; 
+0

Не могли бы вы уточнить, в ближайшее время, на несколько подходов вы пробовали и в какой тип контекста этот код должен поместиться? – nielsj

+5

(Возможно, не самый лучший, но самый короткий из них наверняка;) возможный дубликат [Code golf - hex to (raw) двоичное преобразование] (http://stackoverflow.com/questions/795027/code-golf-hex-to-raw -binary-conversion) – zaf

+0

zaf, это именно то, что я хотел, извините, что раньше этого не видел. Думаю, это будет в некотором роде дубликат этого. – AriX

ответ

2

Является ли строка всегда одинаковой длины?

Если это так:

char *buf = "55 AA 41 2A 00 94 55 AA BB BB 00 FF"; 
sscanf(buf, "%x %x %x [repeat as many times as necessary]", &a, &b, &c [etc]); 

Если нет:

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

int main (int argc, char ** argv) 
{ 
    char *buf = "55 AA 41 2A 00 94 55 AA BB BB 00 FF"; 
    char *p = buf; 
    int i = 0, j; 
    unsigned int *result = calloc(strlen(buf)/3 + 1 * sizeof(int), 1); 

    if (result) 
    { 
     while (sscanf(p, "%02x", &result[i++])) 
     { 
      p += 3; 
      if (p > buf + strlen(buf)) 
      { 
      break; 
      } 
     } 

     printf("%s\n", buf); 

     for (j = 0; j < i; j++) 
     { 
      printf("%02X ", result[j]); 
     } 

     printf("\n"); 
    } 
} 
+0

Работало отлично :) – AriX

+0

Спецификатор преобразования '% 02x' требует указателя на' unsigned int', но вы передаете ему указатель на 'unsigned char'. Это приводит к неопределенному поведению (на практике ваш ответ будет приводить к неправильным результатам на машинах, которые не являются малозначимыми, а также сбоям на машинах со строгими требованиями к выравниванию). – caf

+0

@caf: Хорошо пятнистый. Я отредактирую. – Vicky

1

Пробовали ли вы sscanf или scanf? Эта функция обрабатывает шестнадцатеричные значения и возвращает «необработанные данные».

0
#define GETBITS(a) (a < 'A' ? a - '0' : toupper(a) - 'A' + 10) 

char *cur; 
char data; 
for (cur = buffer; *cur; cur++) { 
    data = GETBITS(cur[0]) << 4 + GETBITS(cur[1]); 
    cur += 2; 
    printf("%c", data); 
} 
printf("\n"); 
0
while(input[i]!='\0'){   
    *(temp++) = ((input[i]>='0' && input[i]<='9')?(input[i]-'0'):(input[i]-'a'+10))*16 +((input[i+1]>='0' && input[i]<='9')?(input[i+1]-'0'):(input[i+1]-'a'+10)); 
     i+=2; 
}