Преобразование шестнадцатеричного кода в строку в C?

Здравствуйте, я использую digi dynamic c. Я пытаюсь преобразовать это в строку

char readingreg[4];
readingreg[0] = 4a;
readingreg[1] = aa;
readingreg[2] = aa;
readingreg[3] = a0;

В настоящее время, когда я делаю операторы printf, это должно быть так:

printf("This is element 0: %x\n", readingreg[0]);

Но я хочу это в строке, чтобы я мог использовать оператор printf, подобный этому

  printf("This is element 0: %s\n", readingreg[0]);

По существу, я отправляю массив readreg через порт TCP/IP, для которого мне нужно иметь его в виде строки. Кажется, я не могу преобразовать его в строку. Спасибо за вашу помощь. Кроме того, если кто-то может сказать мне, как делать каждый элемент за раз, а не весь массив, это было бы хорошо, поскольку будет только 4 элемента.


person Dale Reed    schedule 02.09.2014    source источник
comment
Пожалуйста, уточните, что именно вы хотите, чтобы второй printf() печатал.   -  person James Curran    schedule 02.09.2014
comment
inet_ntoa()   -  person Ryan Haining    schedule 02.09.2014
comment
Используйте snprintf для печати в буфер, а затем напечатайте это? Также помните строку, оканчивающуюся 0 байтом.   -  person hyde    schedule 02.09.2014
comment
Глядя на ответы, я не думаю, что я был ясен, извините. Итак, у меня есть массив, который считывает reg (char), но имеет шестнадцатеричные значения. Я хочу, чтобы его значения были строковыми. Например: readreg[0] = 4a, 4a — это шестнадцатеричное значение, может кто-нибудь помочь мне создать новый массив, и он будет выглядеть так: newArray[0] = 4a; новый массив [1] = аа; и так далее, где 4a и aa будут строками, а не шестнадцатеричными.   -  person Dale Reed    schedule 03.09.2014


Ответы (2)


0xaa переполняется, когда подписано простое char, используйте unsigned char:

#include <stdio.h>

int main(void)
{
    unsigned char readingreg[4];
    readingreg[0] = 0x4a;
    readingreg[1] = 0xaa;
    readingreg[2] = 0xaa;
    readingreg[3] = 0xa0;
    char temp[4];

    sprintf(temp, "%x", readingreg[0]);
    printf("This is element 0: %s\n", temp);
    return 0;
}
person David Ranieri    schedule 02.09.2014
comment
Это дает ошибку. pointer targets in passing argument 1 of ‘sprintf’ differ in signedness [-Werror=pointer-sign]. Вероятно, это предупреждение, но у меня включен Werror. - person Duck Dodgers; 28.01.2021
comment
Ты уверен? в этом коде не задействованы указатели, и я компилирую с предупреждениями о строгости (-Wpedantic -Wall -Wextra -Wmissing-prototypes -Wstrict-prototypes -Wconversion -Wshadow -Wcast-qual -Wnested-externs), а gcc молча компилирует этот фрагмент кода без предупреждений. То же самое для godbolt: godbolt.org/z/9h7rEP без предупреждений. Какой компилятор вы используете? - person David Ranieri; 28.01.2021
comment
@DuckDodgers, теперь я вижу, что ты не ОП, см. комментарий выше, я также пробовал с флагом -Wpointer-sign без предупреждений, в любом случае, если твой компилятор жалуется на подписанность, переключись с char temp[4]; на unsigned char temp[4]; и приведи printf("This is element 0: %s\n", (char *)temp); - person David Ranieri; 28.01.2021
comment
Если я изменю тип данных temp на char, я не получу никаких ошибок. У меня есть gcc8.3.0 на Debian 10. Спасибо за быстрое обновление. Тип данных unsigned char важен только для переменной, хранящей массив байтов, где использование char может привести к переполнению. - person Duck Dodgers; 28.01.2021
comment
Добро пожаловать, у меня есть gcc8.3.0 на Debian 10 - это странно, я также на Debian 10 и не получаю никаких предупреждений, то же самое на моем ноутбуке с Ubuntu 18.04 - person David Ranieri; 28.01.2021
comment
@DavidRanieri Плохо, я неправильно понял смысл кода. Я скоро удалю свои комментарии, чтобы сохранить это в чистоте. - person Chnossos; 06.04.2021

Если ваша машина работает с обратным порядком байтов, вы можете сделать следующее:

char str[9];

sprintf(str, "%x", *(uint32_t *)readingreg);

Если ваша машина с прямым порядком байтов, вам придется поменять порядок байтов:

char str[9];
uint32_t host;

host = htonl(*(uint32_t *)readingreg);
sprintf(str, "%x", host);

Если вас беспокоит переносимость, вам следует использовать второй метод независимо от порядка байтов.

Я получаю следующий вывод:

printf("0x%s\n", str);

0x4аааааа0

person Fiddling Bits    schedule 02.09.2014