Преобразование расширенной строки ASCII в текст на хинди

Я получаю текст строки через USB-связь в Android в виде расширенных символов ASCII, таких как

String receivedText = "5286T11ɬ ªË ¦¿¯¾ ¯¾ ɬ ¨¬°:A011605286 ª¿ª ¾®:12:45 ¸Í®°:(9619441121)ª¿ª:-, ®¹¿¦Í°¾ ¡ ®¹¿¦Í°¾ ª¨À, ¾¦¿µ²À ¸Í, ¾¦¿µ²À ªÂ°Íµ °¿®¾°Í͸:- ¡Í°Éª:-, ¬¾¹°, ¸¾¤¾Í°Â¼ ªÂ°Íµ~";

Теперь эти символы представляют строку на хинди.

Я не понимаю, как преобразовать эту полученную строку в текст, эквивалентный хинди. Любой знает, как преобразовать это в эквивалентный текст на хинди, используя java

Ниже приведен фрагмент кода, который я использую для преобразования массива байтов в строку байтов.

public String byteArrayToByteString(byte[] arayValue, int size) {
        byte ch = 0x00;
        int i = 0;

        if (arayValue == null || arayValue.length <= 0)
            return null;

        String pseudo[] = { "0", "1", "2", "3", "4", "5", "6", "7", "8", "9",
                "A", "B", "C", "D", "E", "F" };
        StringBuffer out = new StringBuffer();

        while (i < size) {

            ch = (byte) (arayValue[i] & 0xF0); // Strip off high nibble
            ch = (byte) (ch >>> 4); // shift the bits down
            ch = (byte) (ch & 0x0F); // must do this is high order bit is on!
            out.append(pseudo[(int) ch]); // convert the nibble to a String
            // Character
            ch = (byte) (arayValue[i] & 0x0F); // Strip off low nibble
            out.append(pseudo[(int) ch]); // convert the nibble to a String
            // Character
            i++;
        }
        String rslt = new String(out);

        return rslt;
    }

Дайте мне знать, если это поможет найти решение

ИЗМЕНИТЬ:

Это кодировка UTF-16, а символы в строке ReceiveText представлены в виде расширенного ASCII для символов хинди.

Новое изменение

у меня новые персонажи

String value = "?®Á?Ƕ ¡??°¿¯¾";

Который говорит मुकेश на хинди и dangaria на хинди. Переводчик Google не переводит дангарию на хинди, поэтому я не могу предоставить вам ее версию на хинди.

Я разговаривал с человеком, занимающимся кодированием, он сказал, что он удалил 2 бита из ввода перед кодированием, т.е. если अ представляет अ на хинди, то он удалил \u09 из ввода и преобразовал оставшиеся 05 в расширенную шестнадцатеричную форму.

Таким образом, новая входная строка, которую я вам предоставил, декодируется в форме приведенного выше объяснения. т. е. \u09 удаляется, а остальные преобразуются в расширенные символы ASCII, а затем отправляются на устройство с помощью USB.

Дайте мне знать, если это объяснение поможет вам найти решение


person Abhinav Singh Maurya    schedule 04.02.2013    source источник
comment
Если это строка Java, это Unicode (UTF-16). Если это что-то другое, это поврежденная строка. Покажите, как вы конвертируете байты с устройства в строки.   -  person McDowell    schedule 04.02.2013
comment
На самом деле эта строка получена от оборудования, которое они используют для отображения текста на хинди, и я думаю, что это текст UTF-16, но я не знаю, как его преобразовать. Я получил его в виде массива байтов, а затем преобразовал его в строку   -  person Abhinav Singh Maurya    schedule 04.02.2013
comment
вы также можете создать свой собственный локальный объект и работать с ним: docs. oracle.com/javase/tutorial/i18n/locale/create.html   -  person SomeJavaGuy    schedule 04.02.2013
comment
Хорошо, но как я могу работать с полученной выше строкой?   -  person Abhinav Singh Maurya    schedule 04.02.2013
comment
@AbhinavSinghMaurya Используйте конструктор строк, который позволяет указать кодировку (набор символов ) или используйте InputStreamReader с тем же, если получаете данные от InputStream.   -  person McDowell    schedule 04.02.2013
comment
@KevinEsche Тип Locale в Java не влияет на кодировку текста.   -  person McDowell    schedule 04.02.2013
comment
Я использовал конструктор строк new String(byte,UTF-16) и вывел результат 긺ㄲ 㨴㔠 슕슸 쎍 슟 슮슰 㨨㤶 㐴 㐴 苂 ꛃ 냂븠 슂슡 슪슨 껂맂 껂맂 껂맂 쎀 쎀 跂鼬 跂鼬 跂鼬 跂鼬 슕슾슂 跂鼬 룃 룃 룃跂鼬 闂 뻂 苂 ꛂ 뿂뗂 닃 껂 뻂냃 跂闃 跂 렺 쎍 슰 쎂 슜슼 ⃂꫃ 苂슂 냃 跂 쎂 슜슼 ⃂꫃슂슂   -  person Abhinav Singh Maurya    schedule 04.02.2013
comment
@AbhinavSinghMaurya Если вы уверены, что это UTF-16, возможно, он не использует сетевой порядок байтов. См. раздел UnicodeBigUnmarked и UnicodeLittleUnmarked.   -  person McDowell    schedule 04.02.2013
comment
Пожалуйста, проверьте мой отредактированный код   -  person Abhinav Singh Maurya    schedule 04.02.2013
comment
Можете ли вы показать, какой на самом деле должна быть полученная строка? Это облегчило бы поиск преобразования, ведущего от одного к другому.   -  person Michał Kosmulski    schedule 25.02.2013
comment
@MichałKosmulski Я разместил это выше в своем вопросе. его полученный текст. Пожалуйста, проверьте это   -  person Abhinav Singh Maurya    schedule 25.02.2013
comment
Я думаю, что @MichałKosmulski хотел посмотреть, какими должны быть персонажи после конвертации. Это то, что вы можете предоставить?   -  person laz    schedule 25.02.2013
comment
@laz, пожалуйста, проверьте мое новое редактирование   -  person Abhinav Singh Maurya    schedule 26.02.2013
comment
Это не слишком мне помогает. Какие необработанные значения байтов должны быть перекодированы в मुकेश?   -  person laz    schedule 26.02.2013
comment
да, их нужно перекодировать в मुकेश   -  person Abhinav Singh Maurya    schedule 26.02.2013
comment
Любые решения? Любой?   -  person Abhinav Singh Maurya    schedule 26.02.2013
comment
Что создает String? Можно ли работать с необработанными байтами, полученными через USB-соединение? Я до сих пор не уверен, что понимаю, в какой кодировке находятся данные из USB-соединения. Вы упоминаете об усечении байтов, что, похоже, приведет к потере данных. Вы также упоминаете кодировку в расширенном ASCII. Это означает ISCII или нет?   -  person laz    schedule 27.02.2013


Ответы (3)


Как правило, для массива байтов, который, как вы знаете, является строковым значением, вы можете использовать следующее.

Предполагая byte[] someBytes:

String stringFromBytes = new String(someBytes, "UTF-16");

Вы можете заменить "UTF-16" на соответствующую кодировку, которую вы можете найти после некоторых экспериментов. Эта ссылка с подробным описанием кодировок символов, поддерживаемых java. может помочь.

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

  • Если вы читаете файл с USB-накопителя, у Android могут быть существующие фреймворки, которые помогут вам сделать это более стандартным способом.
  • Если вам определенно нужно считывать и обрабатывать байты напрямую из USB-порта, убедитесь, что вы знакомы с API/протоколом данных, которые вы читаете. Возможно, некоторые из байтов являются управляющими сообщениями или чем-то подобным, что не может быть преобразовано в строки, и вам нужно будет точно определить, где в потоке байтов начинается (и заканчивается) строка.
person Erik Madsen    schedule 22.02.2013
comment
Я пробовал эту штуку, но пока не удалось преобразовать ее в хинди - person Abhinav Singh Maurya; 25.02.2013
comment
Вы уверены, что весь массив байтов является строковыми данными? Я не знаком с протоколом связи USB, но, может быть, массив включает в себя дополнительные байты, связанные с протоколом? Если это только строковые данные, и вы пробовали все стандартные кодировки Java, то это указывало бы мне, что строка имеет менее стандартную кодировку, и вам нужно было бы выкопать некоторую информацию из ваших спецификаций относительно того, какой может быть эта кодировка. . - person Erik Madsen; 25.02.2013
comment
Я получаю полученный текст (строка из моего вопроса) в виде массива байтов. и я попытался преобразовать его в форму, которую вы написали в своем ответе. Но до сих пор нет выхода. - person Abhinav Singh Maurya; 25.02.2013
comment
Можете ли вы предоставить подпись метода, который вы использовали для получения массива байтов? - person Erik Madsen; 25.02.2013
comment
int com.hoho.android.usbserial.driver.UsbSerialDriver.read(byte[] arg0, int arg1) выдает IOException - person Abhinav Singh Maurya; 25.02.2013
comment
Мне нужно дважды проверить тип UsbSerialDriver, но я бы искал решение, в котором вы обертываете его как входной поток и получаете из него строку. - person Erik Madsen; 25.02.2013
comment
Я не использую входной поток, потому что этот метод чтения UsbSerialDriver возвращает мне массив байтов, а его ответ - int. - person Abhinav Singh Maurya; 25.02.2013
comment
Я изменил свой ответ выше, чтобы описать, как я буду использовать Android USB Host API для чтения строки с USB-устройства. - person Erik Madsen; 25.02.2013
comment
давайте продолжим это обсуждение в чате - person Erik Madsen; 25.02.2013
comment
Я поговорил с коллегой, который больше знаком с Android, и добавил совет, который он дал выше. - person Erik Madsen; 27.02.2013
comment
также я обновил ссылку с кодировками до версии java 6. - person Erik Madsen; 27.02.2013
comment
Проверьте чат Эрика в предыдущем обсуждении чата - person Abhinav Singh Maurya; 27.02.2013

Я немного поиграл с этим и имею представление о том, что вам может понадобиться сделать. Похоже, что значение receivedText, указанное в вашем сообщении, по какой-то причине закодировано в windows-1252. Возможно, это было из-за того, что он вставил это в этот пост. Предоставление необработанных значений байтов было бы лучше, чтобы избежать ошибок кодирования. Тем не менее, мне удалось преобразовать String в следующие символы Unicode Devanagari:

5286T11फए ऋभ इडऒठ ऒठ फए उएओ:A011605286 ऋडऋ ठऍ:12:45 चयऍओ:(9619441121)ऋडऋ:-, ऍछडइयओठ ँ ऍछडइयओठ ऋउढ, ठइडगऑढ चय, ठइडगऑढ ऋतओयग ओडऍठओययच:- ँयओफऋ:-, एठछओ, चठअठयओतञ ऋतओयग~

Со следующим кодом:

final String receivedText = "5286T11ɬ ªË ¦¿¯¾ ¯¾ ɬ ¨¬°:A011605286 ª¿ª ¾®:12:45 ¸Í®°:(9619441121)ª¿ª:-, ®¹¿¦Í°¾ ¡ ®¹¿¦Í°¾ ª¨À, ¾¦¿µ²À ¸Í, ¾¦¿µ²À ªÂ°Íµ °¿®¾°Í͸:- ¡Í°Éª:-, ¬¾¹°, ¸¾¤¾Í°Â¼ ªÂ°Íµ~";

final Charset fromCharset = Charset.forName("x-ISCII91");
final CharBuffer decoded = fromCharset.decode(ByteBuffer.wrap(receivedText.getBytes("windows-1252")));

final Charset toCharset = Charset.forName("UTF-16");
final byte[] encoded = toCharset.encode(decoded).array();
System.out.println(new String(encoded, toCharset.displayName()));

Являются ли это ожидаемые персонажи, вам нужно сказать мне :)

Кроме того, я не уверен, доступна ли кодировка символов x-ISCII91 в Android.

person laz    schedule 25.02.2013
comment
Ваше решение, скорее всего, будет правильным (хотя я никоим образом не знаю хинди). Я искал кодировку, которая предоставила бы рассматриваемую строку при декодировании с использованием кодировки по умолчанию вместо правильной, но, похоже, вы поставили меня на это. Ваше здоровье! - person Michał Kosmulski; 25.02.2013
comment
Очень хорошая попытка @laz, символы на хинди, но вывод неправильный, то есть вывод не на правильном хинди. Я голосую за ваши усилия :) - person Abhinav Singh Maurya; 26.02.2013

hindi = new String(receivedText.getBytes(), "UTF-16");

Но на самом деле это не похоже на хинди. Вы уверены, что это закодировано как UTF-16?

Изменить:

String charset = "UTF-8";
hindi = new String(hindi.getBytes(Charset.forName(charset)), "UTF-16");

Замените UTF-8 фактическим символом, который привел к вашей длинной строке.

person Marc    schedule 04.02.2013
comment
Но способ в целом будет работать. Узнайте, какой набор символов привел к вашему receivedText, затем извлеките байты из вашего текста, используя этот набор символов, затем создайте новую строку из этих байтов и используйте правильную кодировку (может быть UTF-16). - person Marc; 04.02.2013
comment
@MarcMosby предложение кодировать поврежденную строку как UTF-8 и декодировать ее как UTF-16 вряд ли сработает. Данные уже повреждены. Эти операции транскодирования часто являются разрушительными, поскольку недопустимые или неподдерживаемые последовательности преобразуются в символ замены. - person McDowell; 04.02.2013
comment
попробуйте установить системную кодировку utf-16:System.setProperty("file.encoding","UTF-16"); - person SomeJavaGuy; 04.02.2013