我有一个看起来像这样的字符串:
{\x22documentReferer\x22:\x22http:\x5C/\x5C/pikabu.ru\x5C/freshitems.php\x22}
我怎么能把它转换成可读的JSON?
我找到了不同的慢速解决方案,例如here with regEx
已经尝试过:
URL.decode
StringEscapeUtils
JSON.parse // from different libraries
例如,python有一个简单的解决方案,如来自'string_escape'
链接的可能重复适用于Python,我的问题是关于Java或Scala
我正在使用的工作但速度很慢的解决方案来自here:
def unescape(oldstr: String): String = {
val newstr = new StringBuilder(oldstr.length)
var saw_backslash = false
var i = 0
while (i < oldstr.length) {
{
val cp = oldstr.codePointAt(i)
if (!saw_backslash) {
if (cp == '\\') saw_backslash = true
else newstr.append(cp.toChar)
} else {
if (cp == '\\') {
saw_backslash = false
newstr.append('\\')
newstr.append('\\')
} else {
if (cp == 'x') {
if (i + 2 > oldstr.length) die("string too short for \\x escape")
i += 1
var value = 0
try
value = Integer.parseInt(oldstr.substring(i, i + 2), 16)
catch {
case nfe: NumberFormatException =>
die("invalid hex value for \\x escape")
}
newstr.append(value.toChar)
i += 1
}
else {
newstr.append('\\')
newstr.append(cp.toChar)
}
saw_backslash = false
}
}
}
i += 1
}
if (saw_backslash) newstr.append('\\')
newstr.toString
}
private def die(msg: String) {
throw new IllegalArgumentException(msg)
}
答案 0 :(得分:1)
\x
用于在Python和其他语言中转义ASCII字符。在Scala和Java中,您可以使用\u
来转义Unicode字符。由于ASCII是Unicode的一个子集(如here所述),我们可以使用unescapeJava
方法(在StringEscapeUtils
中)以及一些简单的替换来添加\u
转义字符连同2个前导零:
import org.apache.commons.lang3.StringEscapeUtils
StringEscapeUtils.unescapeJava(x.replaceAll("""\\x""", """\\u00"""))
您还可以使用正则表达式查找转义序列,并用适当的ASCII字符替换它们:
val pattern = """\\x([0-9A-F]{2})""".r
pattern.replaceAllIn(x, m => m.group(1) match {
case "5C" => """\\""" //special case for backslash
case hex => Integer.parseInt(hex, 16).toChar.toString
})
这似乎更快,并且不需要外部库,尽管它仍然可能对您的需求很慢。它可能也不包括一些边缘情况,但可能涵盖简单的需求。
我绝对不是这方面的专家,因此可能有更好的方法来解决这个问题。