【问题标题】:jsp utf encodingjsp utf编码
【发布时间】:2010-10-04 01:24:53
【问题描述】:

我很难弄清楚如何处理这个问题:

我正在为一所意大利大学开发一个网络工具,我必须显示带有重音符号的单词(例如 è、ù、...);有时我从 PostgreSql 表(UTF8 编码)中得到这些词,但大多数情况下我必须从文件中读取长段落。这些文件被编码为 utf-8 xml,并在 Smultron 或任何 utf-8 编辑器中显示良好(它们是在 python 旧文件中创建的,具有è 等实体而不是“è”)。

我写了一个 java 类,它从 xml 文件中提取相关段,它的工作原理是这样的:

String s = parseText(filename, position)

如果我将返回的字符串写入文件,一切看起来都很好;问题是,如果我这样做了

out.write(s)

在 jsp 页面中,我得到了奇怪的字符。顺便说一句,我使用

String s = getWordFromPostgresql(...)

out.write(s)

在同一个jsp中,它显示OK。

有什么提示吗?

谢谢 尼古拉


@krosenvold

感谢您的回复,但是该指令已经在页面中,但它不起作用(实际上它“起作用”但仅适用于我从数据库中获取的字符串)。我认为从文件中读取有些东西,但我不明白......它们在“java”中工作,但在“jsp”中不起作用(想不出更好的解释......)

这是从实际代码中提取的一个基本示例:从文件中读取的方法返回一个 Map,从 Mark(表示文本中位置的对象)到 String(包含文本):

这是在 .jsp 页面中(上面的帖子中引用了 utf 指令)

    // ...
    Map<Mark, String> map = TestoMarkParser.parseMarks(...);
    out.write(map.get(m));

结果如下:

“Fu per√≤ cos√¨ in uso il Genere Enharmonico, che quelli quali vi si esercitavano,”

如果我将相同的代码放在一个 java 类中,并将 out.write 替换为 System.out.println,结果是这样的:

“Fu però così in uso il Genere Enharmonico, che quelli quali vi si esercitavano”


我一直在用十六进制编辑器做一些分析,这里是:

原始字符串:“fu però così”

ò 在 xml 文件中: C3 B2

ò 由 jsp 文件中的 out.write() 呈现: E2 88 9A E2 89 A4

ò 通过以下方式写入文件:

FileWriter w = new FileWriter(new File("out.txt"));
w.write(s);     // s is the parsed string
w.close();

C3 B2

将每个字符的值打印为 int

0: 70 = F
1: 117 = u
2: 32 =  
3: 112 = p
4: 101 = e
5: 114 = r
6: 8730 = � 
7: 8804 = � 
8: 32 =  
9: 99 = c
10: 111 = o
11: 115 = s
12: 8730 = �
13: 168 = �
14: 10 = `

【问题讨论】:

标签: java jsp encoding utf


【解决方案1】:

我也遇到了同样的问题,一切都是“utf-8”以及为什么我看到了
无意义的字符,问题出在jsp中 它必须在页面的顶部。

 <%request.setCharacterEncoding("utf-8");%>

一切都会好起来的。

【讨论】:

    【解决方案2】:

    我有一些国际 jsp [有“特殊”国际(相对于英语)字符]。

    在它们的顶部插入这个 [并且只有这个,即:也没有 contentType 指令(导致重复的 contentType 错误)] 可以让它们正确保存和呈现:

    <%@page pageEncoding="UTF-8"%>
    

    这个参考 [http://www.inter-locale.com/codeset1.jsp] 帮助我发现了这一点。

    【讨论】:

    • +1;删除我包含的 JSP 中的重复 contentType 解决了我的问题。我认为重复的页面指令会导致这种不正确的行为有点奇怪..
    【解决方案3】:

    在 jsp 页面指令中,您应该尝试将 content-type 设置为 utf-8,这也会将 pageEncoding 设置为 utf-8。

    <%@page contentType="text/html;charset=UTF-8"%>
    

    UTF-8 不是 jsp 中的默认内容类型,由此引发了各种有趣的问题。问题是底层流默认被解释为 ISO-8859-1 流。如果您将一些 unicode 字节写入此流,它们将被解释为 ISO-8859-1。我发现将编码设置为 utf-8 是最好的解决方案。

    编辑: 此外,java 中的 string 变量应该始终 是 unicode。所以你应该总是可以说

    System.out.println(myString) 
    

    并在您的网络服务器的控制台窗口中看到正确的字符集(或者只是在调试器中停止并检查它)。我怀疑这样做时您会看到不正确的字符,这使我相信您在构造字符串时遇到了编码问题。

    【讨论】:

      【解决方案4】:
      String s = parseText(filename, position)
      

      这个方法是在哪里定义的?我猜这是您自己的方法,它打开文件并提取特定的数据块。在这个过程中的某个地方,它正在从字节转换为字符,可能使用 JVM 的默认编码。

      如果您正在运行的 JVM 的默认编码与文件中的实际编码不匹配,您将在字符串中得到不正确的字符。此外,如果您正在阅读以多字节形式(例如 UTF-8)编码的内容,您的“位置”可能指向多字节编码的中间。

      如果源文件是格式正确的 XML,那么最好使用真正的解析器(例如 JDK 内置的解析器)来解析它们,因为解析器会提供正确的字节转换人物。然后使用 XPath 表达式检索值。

      如果您过去没有使用过 XML 解析器,这里有两个我写在 parsing 和 XPath 上的文档。


      编辑:您可能会发现有用的一件事是打印出字符串中的实际字符值,使用类似以下内容:

      public static void main(String[] argv) throws Exception
      {
          String s = "testing\u20ac";
          for (int ii = 0 ; ii < s.length() ; ii++)
          {
              System.out.println(ii + ": " + (int)s.charAt(ii) + " = " + s.charAt(ii));
          }
      }
      

      您可能还应该打印出您的默认字符集,以便您知道任何特定的字节序列是如何转换为字符的:

      public static void main(String[] argv) throws Exception
      {
          System.out.println(Charset.defaultCharset());
      }
      

      最后,您应该将所服务的页面作为原始字节进行检查,以准确了解返回给客户端的内容。


      编辑 #2:字符 ò 是 Unicode 值 00F2,它将被 UTF-8 编码为 C3 B2。这两个代码与您在之前的答案中显示的符号不对应。

      有关 Unicode 字符的更多信息,请参阅 Unicode.org 上的 code charts。

      【讨论】:

      • parseText 是我定义的示例方法;是的,我使用 SAX 解析,尽管我承认我是 xml 处理的新手;我真的无法理解的是当我使用 java 控制台或打印到 jsp 页面时的区别(相同的 java String 对象呈现不同......)我现在正在查看您的文档,感谢您的参考.
      • 我用十六进制编辑器检查了 xml 文件,我发现 ò 字符在 xml 中被有效地编码为 C3 B2 ...
      • 我想我发现了问题所在;在 SAX 解析器中使用 characters() 方法时可能存在一些转换错误。事实上,重音字符被编码“两次”(即 utf-8 编码的 utf-8 编码)。我切换到一个更简单的 DOM 解析器(它自己处理所有这些细节)并且页面工作正常(感谢您的教程)。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2013-02-02
      • 2011-11-02
      • 2012-07-15
      • 2011-03-27
      • 2015-03-24
      • 2012-09-25
      • 2015-01-02
      相关资源
      最近更新 更多