Java char содержит значение> 255? - PullRequest
2 голосов
/ 22 сентября 2010

Я получаю массив символов из сокета:

char[] cbuf = new char[3];
inputStream.read(cbuf, 0, 3); // read 3 chars in buffer "cbuf", offset = 0

Затем, когда я распечатаю это:

System.out.println("r:"+(int)cbuf[0]+" g:"+(int)cbuf[1]+" b:"+(int)cbuf[2]);

Я получаю в какой-то момент:

...
r:82 g:232 b:250
r:82 g:232 b:250
r:66 g:233 b:8224

Значение 8224 намного больше, чем 255 , как символ может содержать это значение ???

Спасибо

Ответы [ 6 ]

8 голосов
/ 22 сентября 2010

Примитив char в Java шириной 16 бит для размещения символов вне стандартного диапазона ASCII с использованием Unicode .

Похоже, вы пытаетесь сохранить значения RGB в char[3]. Могу ли я предложить byte[3] или java.awt.Color ?

Color c = new Color(255, 255, 240);
7 голосов
/ 22 сентября 2010

Нет метода read(char[], int, int) для InputStream . Вы должны вызывать это в подклассе Reader (например, InputStreamReader ). InputStreamReader автоматически преобразует байты в символы, используя кодировку символов платформы по умолчанию, которая в вашем случае выглядит так: windows-1252 .

Символ, который вы получили, 8224 - это символ Unicode U + 2020 Dagger '†' . Вероятно, это было переведено из байта 0x86 (134) с использованием кодировки символов windows-1252.

Если вы читаете файл, содержащий текст, который не является текстом, вам нужно убедиться, что вы не читаете его с подклассом Reader , но используете подкласс InputStream вместо. В качестве альтернативы вы можете использовать InputStreamReader и указать кодировку символов, например ISO-8859-1 , которая будет сопоставлять каждый байт с символом с одинаковым числовым значением.

5 голосов
/ 22 сентября 2010

Тип char в Java является 16-разрядным.

Если вы ищете 8-битный тип данных, рассмотрите возможность использования byte.

2 голосов
/ 22 сентября 2010

Как уже указывали люди, вы хотите читать байты, а не символы (16-битные символы в Java), и убедиться, что вы действительно используете InputStream, а не Reader.

Я также хочу указать на то, что не имеет прямого отношения к вашему вопросу: при вызове InputStream.read(byte[]) или InputStream.read(byte[], int, int) для чтения нескольких байтов не предполагайте, что все запрошенные байты были прочитаны при возврате. Вызов read может вернуться, как только будет доступно байт. Вы всегда должны проверять возвращаемое значение, чтобы узнать, сколько байтов действительно было прочитано.

То же самое относится к read методам в Reader.

1 голос
/ 22 сентября 2010

Java использует UTF (не ASCII) для хранения символов, UTF имеет длину 16 бит, поэтому он может содержать значения до 65,535.

0 голосов
/ 29 июля 2012

Символы - это 16-битные целые числа без знака в Java. Хотя технически, если вы получаете значения из ненадежного байт-кода, вы должны быть готовы работать с произвольными 32-битными значениями, так как JVM не проверяет диапазоны целочисленных аргументов.

...