Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/oracle/10.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
从Oracle数据库中使用Java读取特殊字符(æ;ø;å;)_Java_Oracle_Character Encoding - Fatal编程技术网

从Oracle数据库中使用Java读取特殊字符(æ;ø;å;)

从Oracle数据库中使用Java读取特殊字符(æ;ø;å;),java,oracle,character-encoding,Java,Oracle,Character Encoding,我在从oracle数据库读取特殊字符时遇到问题(使用JDBC驱动程序和glassfish tooplink) 我通过WebService在数据库中存储名称“GRØNLÅEN KJÆTIL”,并且在数据库中正确存储数据 但当我读取此字符串时,在日志文件上打印并将其转换为字节数组,代码如下: int pos = 0; byte[] msg=new byte[1024]; String F = "F" + passenger.getName(); logger.debug("Add " +

我在从oracle数据库读取特殊字符时遇到问题(使用JDBC驱动程序和glassfish tooplink)

我通过WebService在数据库中存储名称“GRØNLÅEN KJÆTIL”,并且在数据库中正确存储数据

但当我读取此字符串时,在日志文件上打印并将其转换为字节数组,代码如下:

 int pos = 0;
 byte[] msg=new byte[1024];

 String F = "F" + passenger.getName();
 logger.debug("Add " + F + " " + F.length());
 msg = addStringToArrayBytePlusSeparator(msg, F,pos);

private byte[] addStringToArrayBytePlusSeparator(byte[] arrDest,String strToAdd,int destPosition)
    {
        System.arraycopy(strToAdd.getBytes(Charset.forName("ISO-8859-1")), 0, arrDest, destPosition, strToAdd.getBytes().length);

        arrDest = addSeparator(arrDest,destPosition+strToAdd.getBytes().length,1);

        return arrDest;
    }
1) 日志文件中有:“Add FGRÃNLÔ(名称不正确,未打印F.length()

2) 代码抛出: java.lang.ArrayIndexOutOfBoundsException 位于java.lang.System.arraycopy(本机方法) 在it.edea.ebooking.business.chi.control.VingCardImpl.addStringToArrayBytePlusSeparator(Test.java:225)上

有解决办法吗


Tanks

您在
System.arraycopy
调用中调用的
stroAdd.getBytes()
没有指定字符编码-这将使用系统默认编码,可能不是ISO-8859-1。您应该使用一致的编码。坦白地说,如果你有选择的话,我也建议你使用UTF-8而不是ISO-8859-1,但那是另一回事

现在为什么要处理字节数组?为什么不用字符串呢

还要注意的是,您的
addStringToArrayBytePlusSeparator
方法没有给出它被复制了多少字节的任何指示,这意味着调用方不知道以后该如何处理它。如果必须这样使用字节数组,我建议让
addStringToArrayBytePlusSeparator
返回新的“逻辑数组结尾”或复制的字节数。例如:

private static final Charset ISO_8859_1 = Charset.forName("ISO-8859-1");

/**
 * (Insert fuller description here.)
 * Returns the number of bytes written to the array
 */
private static int addStringToArrayBytePlusSeparator(byte[] arrDest,
                                              String strToAdd,
                                              int destPosition)
{
    byte[] encodedText = ISO_8859_1.getBytes(strToAdd);
    // TODO: Verify that there's enough space in the array 

    System.arraycopy(encodedText, 0, arrDest, destPosition, encodedText.length);

    return encodedText.length;
}

编码/解码问题很难解决。在每个过程步骤中,您都必须进行正确的编码/解码。所以

  • 熟悉字节(inputstream)和字符(读卡器、字符串)的差异
  • 选择要在数据库中存储数据的字符编码,以及要公开Web服务的字符编码。确保在数据库中加载初始数据时,其编码正确
  • 使用正确的数据库属性进行连接。mysql需要添加到连接url:
    ?useUnicode=true&;characterEncoding=UTF-8
    当使用UTF-8时,我对oracle一无所知
  • 如果您在某个特定步骤中打印/调试,并且看起来正常,则无法确定是否正确执行了该步骤。记录器可能会使用错误的编码进行写入(有时会使某些内容看起来正常,但实际上它已损坏)。您的终端可能无法正确处理奇怪的字节编码。命令行数据库客户端也是如此。数据可能存储错误,但配置错误的终端会将数据解释/显示为正确
  • 在XML中,重要的不仅仅是流编码,还有XML编码属性

  • 如果我在Windows操作系统中运行这个项目,这个工作很好,但是在Linux系统上这个问题仍然存在!