一、Google 的Gson的排序策略(来自网络)
private static Comparator<String> getComparator() {
Comparator<String> c = new Comparator<String>() {
@Override
public int compare(String o1, String o2) {
return o1.compareTo(o2);
}
};
return c;
}
public static void sort(JsonElement e) {
if (e.isJsonNull()) {
return;
}
if (e.isJsonPrimitive()) {
return;
}
if (e.isJsonArray()) {
JsonArray a = e.getAsJsonArray();
for (Iterator<JsonElement> it = a.iterator(); it.hasNext(); ) {
sort(it.next());
}
return;
}
if (e.isJsonObject()) {
Map<String, JsonElement> tm = new TreeMap<String, JsonElement>(getComparator());
for (Map.Entry<String, JsonElement> en : e.getAsJsonObject().entrySet()) {
tm.put(en.getKey(), en.getValue());
}
for (Map.Entry<String, JsonElement> en : tm.entrySet()) {
e.getAsJsonObject().remove(en.getKey());
e.getAsJsonObject().add(en.getKey(), en.getValue());
sort(en.getValue());
}
return;
}
}
public static String sortJsonForKey(String json) {
// Gson gson= new GsonBuilder().setPrettyPrinting().create(); 这行可以格式化输出json
Gson gson=new Gson();
JsonParser p = new JsonParser();
JsonElement e = p.parse(json);
sort(e);
return gson.toJson(e);
}
二、阿里的fastjson,没有上面那么繁琐
public static String sortJson(String streamStr) {
//Feature.OrderedField防止乱序
JSONObject paramJson = JSONObject.parseObject(streamStr, Feature.OrderedField);
//true 表示需要排序
JSONObject sortParamJson = new JSONObject(true);
for (Map.Entry<String, Object> dataMap : paramJson.entrySet()) {
sortParamJson.put(dataMap.getKey(), dataMap.getValue());
}
return sortParamJson.toJSONString();
}
fastjson 的JSONObject的源码中有这一段,他会根据需不需要排序去选择不同的Map
public JSONObject(int initialCapacity){
this(initialCapacity, false);
}
public JSONObject(int initialCapacity, boolean ordered){
if (ordered) {
map = new LinkedHashMap<String, Object>(initialCapacity);
} else {
map = new HashMap<String, Object>(initialCapacity);
}
}
注意:千万不要用new JSONObject(TreeMap()),在安卓和java后端排序的结果不一致的,大坑
说到json再推荐两个实用的工具方法
1、json格式化输出,可以在logcat看到格式化后的json,也可以格式化保存到文件中
public static String stringToJSON(String strJson) {
// 计数tab的个数
int tabNum = 0;
StringBuffer jsonFormat = new StringBuffer();
int length = strJson.length();
char last = 0;
for (int i = 0; i < length; i++) {
char c = strJson.charAt(i);
if (c == '{') {
tabNum++;
jsonFormat.append(c + "\n");
jsonFormat.append(getSpaceOrTab(tabNum));
} else if (c == '}') {
tabNum--;
jsonFormat.append("\n");
jsonFormat.append(getSpaceOrTab(tabNum));
jsonFormat.append(c);
} else if (c == ',') {
jsonFormat.append(c + "\n");
jsonFormat.append(getSpaceOrTab(tabNum));
} else if (c == ':') {
jsonFormat.append(c + " ");
} else if (c == '[') {
tabNum++;
char next = strJson.charAt(i + 1);
if (next == ']') {
jsonFormat.append(c);
} else {
jsonFormat.append(c + "\n");
jsonFormat.append(getSpaceOrTab(tabNum));
}
} else if (c == ']') {
tabNum--;
if (last == '[') {
jsonFormat.append(c);
} else {
jsonFormat.append("\n" + getSpaceOrTab(tabNum) + c);
}
} else {
jsonFormat.append(c);
}
last = c;
}
return jsonFormat.toString();
}
// 是空格还是tab
private static String getSpaceOrTab(int tabNum) {
StringBuffer sbTab = new StringBuffer();
for (int i = 0; i < tabNum; i++) {
sbTab.append('\t');
}
return sbTab.toString();
}
public static void main(String[] array){
String json={"name":"test","age":18};
json=stringToJSON(json);
System.out.print(json);
//输出结果:{"name":"闯天涯",
// "age":18
// }
}
2、json包含中文的时候在logcat输出的是Unicode编码的问题
public static String unicode2UTF8(String src) {
if (null == src) {
return null;
}
StringBuilder out = new StringBuilder();
for (int i = 0; i < src.length(); ) {
char c = src.charAt(i);
if (i + 6 < src.length() && c == '\\' && src.charAt(i + 1) == 'u') {
String hex = src.substring(i + 2, i + 6);
try {
out.append((char) Integer.parseInt(hex, 16));
} catch (NumberFormatException nfe) {
nfe.fillInStackTrace();
}
i = i + 6;
} else {
out.append(src.charAt(i));
++i;
}
}
return out.toString();
}
public static void main(String[] array){
String json={"name":"\u95ef\u5929\u6daf","age":18};
json=unicode2UTF8(json);
System.out.print(json);
//输出结果:{"name":"闯天涯","age":18}
}
要是在logcat格式化输出json,并将json中的unicode转成中文可以如下操作
unicode2UTF8(stringToJSON(json))