翻译字符串的编码

Translate encoding of string

我有一个 Windows-1252 编码的字符串,但需要转换为 UTF-8。

这是一个修复 UTF-8 文件的程序,该文件的字段包含以 quoted-printable Windows-1252. Here's the code that decodes the quoted-printable 编码的俄语文本:

(defn reencode
    [line]
    (str/replace line #"=([0-9A-Fa-f]{2})=([0-9A-Fa-f]{2})"
        (fn [match] (apply str
            (map #(char (Integer/parseInt % 16)) (drop 1 match))))))

这是最终代码:

(defn reencode
    [line]
    (str/replace line #"(=([0-9A-Fa-f]{2}))+"
        (fn [[match ignore]]
            (String.
                (byte-array (map
                    #(Integer/parseInt (apply str (drop 1 %)) 16)
                    (partition 3 match)))
                "Windows-1252"))))

它使用 (String. ... "Encoding") 修复了所有连续运行的引用打印编码字符的编码。原始函数试图解码对,因此它会跳过 =3D 之类的东西,它是 =.

的引用可打印实体

从磁盘转换 Windows-1252 字符串的最佳方法是使用底层 Java 原语。

(def my-string (String. bytes-from-file "Windows-1252"))

将 return 给你一个 Java 字符串,它已经用 Windows-1252 Charset 解码了字节。从那里你可以用

使用 UTF-8 编码吐出字节
(.getBytes my-string "UTF-8")

更仔细地解决你的问题,如果你有一个混合编码的文件,那么你可以计算出每个编码的分隔符,并使用上面的方法分别读取每组字节。

编辑:Windows-1252 字符串已使用引号打印编码。您首先需要解码它,使用您的函数或者更优选使用 Apache Commons Codec using QuotedPrintable decode,传递 Windows-1252 字符集。这将 return 一个 Java 字符串,您可以直接对其进行操作而无需进一步转换。

N.B。对于某种类型安全措施,在指定要使用的字符集时,您可能应该使用 Java Charset 对象而不是字符串(字符串 class 可以采用任何一种)。