Неожиданные символы при чтении данных из массива сокетов в байты

Я получаю данные от UDP использование порта C ++ программирование. Предположим, мы получаем данные сокета char buf[2000], Когда я печатаю данные (преобразованные в шестнадцатеричный код), в сообщениях появляются неожиданные данные. Например, запустив код:

for (int i =0 ; i < 2000; i++)
{
printf(" ");
printf("%02x", buf[i]);
}

выход:

EF BF BD 01 00 1C 1E 39 5A 18 40 EF BF BD 00 38 51 EF BF BD 00 00 EF BF BD EF BF BD 00 48 00 EF BF BD 00 00 00 64 EF BF BD 1F

EF BF BD шаблон в коде неожиданный и лишний.
Для решения этой проблемы я конвертирую char в unsigned char и используя код:

for (int i =0 ; i < 2000; i++)
{
printf(" ");
printf("%02x", (unsighed char)buf[i]);
}

Теперь вывод содержит желаемый результат:

aa 01 00 1c 1e 39 5a 18 50 fc 00 61 47 ae 00 00 ff b6 00 4e 01 f4 00 00 00 64 b5 4f

(Обратите внимание, что выходы для разных сообщений)

После этого я пишу сообщения Кафке. Проблема в том, что когда я читаю сообщения от Кафки, на этот раз с использованием программирования Java используя следующие коды:

ConsumerRecords<String, String> records = kafkaConsumer.poll(100);
for (ConsumerRecord<String, String> record : records) {
byte[] temp = record.value().getBytes();
StringBuffer result = new StringBuffer();
for (byte b : temp) {
result.append(String.format("%02X ", b));
result.append(" "); // delimiter
}
System.out.println(result);

и вывод:

EF BF BD 01 00 1C 1E 39 5A 18 40 EF BF BD 00 38 51 EF BF BD 00 00 EF BF BD EF BF BD 00 48 00 EF BF BD 00 00 00 64 EF BF BD 1F

снова с дополнительным EF BF BD нежелательный образец.

Итак главный вопрос как я могу изменить код Java печатать сообщения правильным способом, точно так же, как я делал в C ++.

-1

Решение

Вы, кажется, читаете байты, которые используют однобайтовую кодировку для представления текста (например, ISO-8859-1 или windows-1252), но вы решаете читать их, используя библиотечные функции, которые предполагают, что эти байты представляют собой представление UTF-8 текст.

«Aa» не является допустимым начальным байтом для представления символа в UTF-8. Какой бы механизм вы не использовали для преобразования байтов в символы, это знает и вставляет , Символ замены Юникода, как указание неверного ввода.

UTF-8 представление это три байта ‘ef bf bd’.

Всегда указывайте правильную кодировку при преобразовании между байтами и символами. Это не проблема в коде, который вы показали в своем вопросе; скорее это проблема с кодом, который читает байты и конвертирует их в значение String, которое record.value(), Это тот код, который интерпретировал байт ‘aa’ как искаженную последовательность UTF-8 и поместил в вашей строке, чтобы указать на проблему.

Этот код, если он на Java, вероятно, используется new String(bytes), Следовало бы использовать new String(bytes, StandardCharsets.ISO_8859_1) (или возможно new String(bytes, "windows-1252") или какой-то другой однобайтовой кодировки).

Когда вы преобразуете строку обратно в байты, применяются те же правила. Если вы хотите ª Чтобы символ был декодирован в один байт «aa», необходимо использовать однобайтовую кодировку:

record.value().getBytes(StandardCharsets.ISO_8859_1)

Как я уже сказал, в настоящее время record.value () не начинается с ªначинается с , record.value (). getBytes () использует кодировку вашей системы по умолчанию (UTF-8), поэтому первые три байта возвращаемого массива являются представлением UTF-8 , который «EF BF BD».

1

Другие решения

Других решений пока нет …

По вопросам рекламы [email protected]