Почему получение символа ® (U + 00AE) отличается в Java 6 и Java 7? - PullRequest
0 голосов
/ 29 января 2019

Это мой первый вопрос в StackOverFlow.Я не очень хорошо владею английским языком.Пожалуйста, извините.

У меня проблема с тем, что мое приложение возвращает странный символ.

PlayStation \ ufffd \ ufffd4 Pro

Itдолжно быть примерно так:

PlayStation®4 Pro

Я думаю, что символ '\ ufffd' представляет this, 'REPLACE CHARACTER'.

Мое приложение использует jdk 1.6.

Я обнаружил, что когда я изменяю jdk моего приложения на 1.7, он правильно печатает символ.

PlayStation®4 Pro

Дополнительная информация

Мое приложение использует ibatis, и проблема возникает после queryForObject.

public class A {
    private String content;
    public String getContent() {
        return content;
    }
}
A a = (A)queryForObject("mapper.getSomething", params);
return a;
// jdk1.6 - a.getContent() : PlayStation\ufffd\ufffd4 Pro
// jdk1.7 - a.getContent() : PlayStation®4 Pro

Свойство JDBC-соединения похоже наthis.

driverClassName=com.mysql.jdbc.Driver
url=jdbc:mysql://{IPADDRESS}/{DBNAME}?Unicode=true&characterEncoding=MS949&zeroDateTimeBehavior=convertToNull&socketTimeout=500000&connectTimeout=500000

Дополнительная информация 2

  • Я тестировал без ibatis и других.Непосредственное использование соединения jdbc, но тот же результат.
public class CharacterEncodeTest {
    // JDBC driver name and database URL
    static final String DB_URL = "jdbc:mysql://{IPADDRESS}/{DBTNAME}}?Unicode=true&characterEncoding=MS949&zeroDateTimeBehavior=convertToNull&socketTimeout=500000&connectTimeout=500000";

    //  Database credentials
    static final String USER = "{USER}";
    static final String PASS = "{PASSWORD}";

    public static void main(String[] args) {
        Connection conn = null;
        Statement stmt = null;
        try {
            //STEP 2: Register JDBC driver
            Class.forName("com.mysql.jdbc.Driver");

            //STEP 3: Open a connection
            System.out.println("Connecting to a selected database...");
            conn = DriverManager.getConnection(DB_URL, USER, PASS);
            System.out.println("Connected database successfully...");

            //STEP 4: Execute a query
            System.out.println("Creating statement...");
            stmt = conn.createStatement();

            String sql = "SELECT * from TABLE";
            ResultSet rs = stmt.executeQuery(sql);
            //STEP 5: Extract data from result set
            while (rs.next()) {
                //Retrieve by column name
                String content = rs.getString("content");

                //Display values
                System.out.print("content: " + content);
                // jdk1.6 : PlayStation\ufffd\ufffd4 Pro
                // jdk1.7 : PlayStation®4 Pro
            }
            rs.close();
        } catch (SQLException se) {
            // something
        } finally {
            // something
        }//end try
    }
}

Вопрос

Единственное отличие заключается в только при изменении версии jdk .

  1. В чем разница между jdk 1.6 и 1.7 по поводу этой проблемы?

  2. Есть ли решение этой проблемы в jdk 1.6?

Ответы [ 4 ]

0 голосов
/ 29 января 2019

Изначально у вас есть два знака вопроса.Похоже, что был один символ UTF8, но ваш код не смог прочитать 4-байтовую последовательность и, таким образом, показал 2 знака вопроса, каждый из которых представляет неизвестный 2-байтовый символ.Вы уверены, что данные не изменились, пока ваш код не смог обработать UTF8?Это мог быть этот 4-байтовый символ раньше: https://en.wikipedia.org/wiki/Enclosed_R?

0 голосов
/ 29 января 2019

Понятия не имею, но я думаю, что в jdk 1.6 и jdk 1.7 используются разные типы кодировки символов.Пожалуйста, перейдите по ссылкам ниже:

Использует ли Java 1.7 другую кодировку символов?

Почему моя строка возвращает "\ ufffd \ ufffdN ame"

0 голосов
/ 29 января 2019

Если для одного специального символа видны два символа замены (for или?), То двоичные данные UTF-8 были преобразованы в двухбайтовую последовательность, каждый байт> 127 и необратимыми в символ в однобайтовой кодировке.только зная 256 символов.

Таким образом, строка (Unicode) была преобразована в байты UTF-8, а затем эти байты преобразованы в некоторую однобайтовую кодировку.

Это может быть параметр URL, закодированный какUTF-8, полученный как ISO-8859-1.Или какое-то другое вмешательство.URL.Декодирование / кодирование URL получило параметр encoding.Скорее всего, произошли изменения и в окружающей среде.Если в коде java используется ®, редактор должен иметь ту же кодировку, что и компилятор javac, и иметь возможность представлять символ (проверьте, используя вместо этого \u00AE).

Поиск кодировки по умолчанию использует:

  • string.getBytes()
  • new String(bytes)
  • URLDecoder.decode(string)
  • URLEncoder.encode(string)
  • FileReader/FileWriter
  • InputStreamReader(inputStream)
  • OutputStreamWriter(outputStream)

Также zip обработка получила поддержку Unicode для имен файлов.

Anti-pattern:

  • new String(string.getBytes(...), ...)
0 голосов
/ 29 января 2019

Понятия не имею, что такое \ ufffd, но символ ® - это \ u00ae: https://www.fileformat.info/info/unicode/char/00ae/index.htm

...