java中如何忽略字符串中的转义字符--转载

原文地址:http://my.oschina.net/u/1010578/blog/366252

起因

    这几天工作上需要跟另一个同事联调rest接口,我这边是java他是PHP,返回报文是json格式。接口调用成功后,输出返回的报文中有类似“\u79fb\u52a8\u4e92\u8054\u7f51\u5e94\u7528 ”的Unicode字符,有点纳闷,记得java是会自动转换Unicode字符为中文才对。

    通过断点debug一看,发现返回的报文在程序中被转换为“\u79fb\u52a8\u4e92\u8054\u7f51\u5e94\u7528”,两个反斜杠表示字符‘\’,所以输出的不是Unicode对应的中文,而是“像Unicode”的字符串了。

解决方

    只要把得到的报文中的“\”换成“\”,我想就能正常地将Unicode输出中文了,首先想到的是使用字符串的replaceAll()方法。使用replaceAll(“\\“,“\“),但是发现输出结果没有任何变化。 查了下api文档,replaceAll()方法的定义是:

    也就是第一个参数指的是正则表达式,所以“\\”用正则表达式的方式来看,匹配的是字符串中的两个\字符,而不是java中的‘\’转义符。换句话说,就是regex参数作为正则表达式查找的源字符串是已经转义过的“\u79fb\u52a8\u4e92\u8054\u7f51\u5e94\u7528”,而不是转义前的“\\u79fb\\u52a8\\u4e92\\u8054\\u7f51\\u5e94\\u7528”,所以replaceAll(“\\“,“\“)自然没效果了。

    后来在StackOverFlow上找到一个忽略转义的工具类, org.apache.commons.lang.StringEscapeUtils ,里面有忽略各种语言的转义符号的方法,既好用也便于理解,就直接拿来用了。 其中unescapeJava(String s)方法是来处理java转义字符的,可以将字符串中的 “\”转换为 “\”,“'”转换为“'”等。通过这个方法处理以上字符串,刚好能够满足我的需求。

test()public static void main(String<span class="hljs-special"&gt;[<span class="hljs-special"&gt;] args) <span class="hljs-special"&gt;{
    String s = "<span class="hljs-command"&gt;\\u79fb<span class="hljs-command"&gt;\\u52a8<span class="hljs-command"&gt;\\u4e92<span class="hljs-command"&gt;\\u8054<span class="hljs-command"&gt;\\u7f51<span class="hljs-command"&gt;\\u5e94<span class="hljs-command"&gt;\\u7528";
    String s2 = StringEscapeUtils.u<a href="https://www.jb51.cc/tag/nes/" target="_blank" class="keywords">nes</a>capeJava(s);
    Sy<a href="https://www.jb51.cc/tag/stem/" target="_blank" class="keywords">stem</a>.out.println(s);
    Sy<a href="https://www.jb51.cc/tag/stem/" target="_blank" class="keywords">stem</a>.out.println(s2);

<span class="hljs-special"&gt;}

<span class="hljs-special">}

输出结果:
<span class="hljs-command">\u79fb<span class="hljs-command">\u52a8<span class="hljs-command">\u4e92<span class="hljs-command">\u8054<span class="hljs-command">\u7f51<span class="hljs-command">\u5e94<span class="hljs-command">\u7528
移动互联网应用

    附上unescapeJava()方法处理转义字符的相关源码,便于理解。

nescapeJava(Writer out,String str) galArgumentException(    <span class="hljs-keyword"&gt;for(<span class="hljs-keyword"&gt;int i = <span class="hljs-number"&gt;0; i < sz; ++i) {
        <span class="hljs-keyword"&gt;char ch = str.ch<a href="https://www.jb51.cc/tag/ara/" target="_blank" class="keywords">ara</a>t(i);
        <span class="hljs-keyword"&gt;if(inUnicode) {
            unicode.<span class="hljs-keyword"&gt;append(ch);
            <span class="hljs-keyword"&gt;if(unicode.length() == <span class="hljs-number"&gt;4) {
                <span class="hljs-keyword"&gt;try {
                    <span class="hljs-keyword"&gt;int nfe = Integer.parseInt(unicode.toString(),<span class="hljs-number"&gt;16);
                    out.<span class="hljs-keyword"&gt;write((<span class="hljs-keyword"&gt;char)nfe);
                    unicode.setLength(<span class="hljs-number"&gt;0);
                    inUnicode = <span class="hljs-keyword"&gt;false;
                    hadSlash = <span class="hljs-keyword"&gt;false;
                } <span class="hljs-keyword"&gt;catch (NumberFormatException var9) {
                    <span class="hljs-keyword"&gt;throw <span class="hljs-keyword"&gt;new <a href="https://www.jb51.cc/tag/nes/" target="_blank" class="keywords">nes</a>tableRuntimeException(<span class="hljs-string"&gt;"Unable to parse unicode value: " + unicode,var9);
                }
            }
        } <span class="hljs-keyword"&gt;else <span class="hljs-keyword"&gt;if(hadSlash) {
            hadSlash = <span class="hljs-keyword"&gt;false;
            <span class="hljs-keyword"&gt;switch(ch) {
                <span class="hljs-keyword"&gt;case <span class="hljs-string"&gt;'\"':
                    out.<span class="hljs-keyword"&gt;write(<span class="hljs-number"&gt;34);
                    <span class="hljs-keyword"&gt;break;
                <span class="hljs-keyword"&gt;case <span class="hljs-string"&gt;'\'':
                    out.<span class="hljs-keyword"&gt;write(<span class="hljs-number"&gt;39);
                    <span class="hljs-keyword"&gt;break;
                <span class="hljs-keyword"&gt;case <span class="hljs-string"&gt;'\\':
                    out.<span class="hljs-keyword"&gt;write(<span class="hljs-number"&gt;92);
                    <span class="hljs-keyword"&gt;break;
                <span class="hljs-keyword"&gt;case <span class="hljs-string"&gt;'b':
                    out.<span class="hljs-keyword"&gt;write(<span class="hljs-number"&gt;8);
                    <span class="hljs-keyword"&gt;break;
                <span class="hljs-keyword"&gt;case <span class="hljs-string"&gt;'f':
                    out.<span class="hljs-keyword"&gt;write(<span class="hljs-number"&gt;12);
                    <span class="hljs-keyword"&gt;break;
                <span class="hljs-keyword"&gt;case <span class="hljs-string"&gt;'n':
                    out.<span class="hljs-keyword"&gt;write(<span class="hljs-number"&gt;10);
                    <span class="hljs-keyword"&gt;break;
                <span class="hljs-keyword"&gt;case <span class="hljs-string"&gt;'r':
                    out.<span class="hljs-keyword"&gt;write(<span class="hljs-number"&gt;13);
                    <span class="hljs-keyword"&gt;break;
                <span class="hljs-keyword"&gt;case <span class="hljs-string"&gt;'t':
                    out.<span class="hljs-keyword"&gt;write(<span class="hljs-number"&gt;9);
                    <span class="hljs-keyword"&gt;break;
                <span class="hljs-keyword"&gt;case <span class="hljs-string"&gt;'u':
                    inUnicode = <span class="hljs-keyword"&gt;true;
                    <span class="hljs-keyword"&gt;break;
                <span class="hljs-keyword"&gt;default:
                    out.<span class="hljs-keyword"&gt;write(ch);
            }
        } <span class="hljs-keyword"&gt;else <span class="hljs-keyword"&gt;if(ch == <span class="hljs-number"&gt;92) {
            hadSlash = <span class="hljs-keyword"&gt;true;
        } <span class="hljs-keyword"&gt;else {
            out.<span class="hljs-keyword"&gt;write(ch);
        }
    }

    <span class="hljs-keyword"&gt;if(hadSlash) {
        out.<span class="hljs-keyword"&gt;write(<span class="hljs-number"&gt;92);
    }

}

}

相关文章

HashMap是Java中最常用的集合类框架,也是Java语言中非常典型...
在EffectiveJava中的第 36条中建议 用 EnumSet 替代位字段,...
介绍 注解是JDK1.5版本开始引入的一个特性,用于对代码进行说...
介绍 LinkedList同时实现了List接口和Deque接口,也就是说它...
介绍 TreeSet和TreeMap在Java里有着相同的实现,前者仅仅是对...
HashMap为什么线程不安全 put的不安全 由于多线程对HashMap进...