安卓下通常采用以下几种方式解析json数据:
-----------------------------------------------
1.org.json包(已经集成到android.jar中了)
2.google提供的gson库
3.阿里巴巴的fastjson库
4.json-lib
----------------------------------------------
服务器端一般采用json-lib包来构建/解析json,但由于此方法需要导入很多依赖包,所以不建议在android设备上使用。下面重点介绍org.json以及gson解析json数据的方式(
json-lib使用参照:JSON快速入门):
------------------------------------------------------------------------------------------
首先来看四种典型的json数据:
1.bean对象:
{"age":20,"id":1,"job":"程序员","name":"张三"}
2.List<Bean>集合:
[{"age":20,"id":1,"job":"程序员","name":"张三"},{"age":22,"id":2,"job":"经理","name":"李四"},{"age":22,"id":3,"job":"学生","name":"rowandjj"},{"age":22,"id":4,"job":"学生","name":"小巩"},{"age":21,"id":6,"job":"程序员","name":"李卫"}]
3.List<Object>集合:
["rowandjj","小巩","张三","李卫","李四"]
4.List<Map<K,V>>型
[{"name":"张三","job":"程序员"},{"name":"李四","job":"经理"},{"name":"rowandjj","job":"学生"},{"name":"小巩","job":"学生"},{"name":"李卫","job":"程序员"}]
下面采用两种方式解析
1.org.json:
使用方式跟json-lib差不多,也有JsonObject,JsonArray类。
解析步骤:
(1)
根据json的类型(对象/数组)构建jsonObject或者JsonArray对象
JSONObject jsonObj = new JSONObject(String json);
JSONArray jsonArr = new JSONArray(String json);
当然jsonArray对象也可看成jsonObject对象,调用jsonObjec.toJsonArray(String key)即可返回jsonArray对象。
(2)
使用get方法获取json串中对应的数据
jsonObject提供诸如getInt,getString等方法用来获取json中的信息。
jsonArray可以通过get(index)/getJsonObject(index)获取指定位置的json数据。
下面就上面四种类型的json格式分别进行解析,并封装的javabean对象中。
bean:
public class Person//set/get略去
{
private int age;
private int id;
private String name;
private String job;
}
解析:
/**
* 解析第一种格式的json数据:
*/
public static Person json2Person(String json)
{
if(json==null || json.trim().length() == 0)
{
return null;
}
Person p = null;
try
{
p = new Person();
JSONObject jsonObj = new JSONObject(json);
p.setId(jsonObj.getInt("id"));
p.setName(jsonObj.getString("name"));
p.setJob(jsonObj.getString("job"));
p.setAge(jsonObj.getInt("age"));
} catch (JSONException e)
{
e.printStackTrace();
}
return p;
}
/**
* 解析第2种格式的json数据:
*/
public static List<Person> json2Persons(String json)
{
if(json==null || json.trim().length() == 0)
{
return null;
}
List<Person> list = null;
Person p = null;
try
{
list = new ArrayList<Person>();
JSONArray jsonArr = new JSONArray(json);
for(int i = 0 ; i < jsonArr.length();i++)
{
JSONObject jo = jsonArr.getJSONObject(i);
p = new Person();
p.setId(jo.getInt("id"));
p.setAge(jo.getInt("age"));
p.setJob(jo.getString("job"));
p.setName(jo.getString("name"));
list.add(p);
p = null;
}
} catch (JSONException e)
{
e.printStackTrace();
}
return list;
}
/**
* 解析第3种格式的json数据:
*/
public static List<String> json2Names(String json)
{
if(json==null || json.trim().length() == 0)
{
return null;
}
List<String> names = null;
try
{
names = new ArrayList<String>();
JSONArray jsonArr = new JSONArray(json);
for(int i = 0; i < jsonArr.length(); i++)
{
names.add(jsonArr.getString(i));
}
} catch (Exception e)
{
e.printStackTrace();
}
return names;
}
/**
* 解析第4种格式的json数据:
*/
public static List<Map<String,String>> json2NameJobs(String json)
{
if(json==null || json.trim().length() == 0)
{
return null;
}
List<Map<String,String>> namejobs = null;
Map<String,String> map = null;
try
{
namejobs = new ArrayList<Map<String,String>>();
JSONArray jsonArr = new JSONArray(json);
for(int i = 0; i < jsonArr.length(); i++)
{
map = new HashMap<String,String>();
map.put("name",jsonArr.getJSONObject(i).getString("name"));
map.put("job",jsonArr.getJSONObject(i).getString("job"));
namejobs.add(map);
map = null;
}
} catch (Exception e)
{
e.printStackTrace();
}
return namejobs;
}
2.Gson方式解析
两种方式解析,一种是通过jsonReader、jsonWriter,另一种就是我们下面要讲的:
步骤:
1.构建gson对象:
Gson gson = new Gson();
2.调用fromJson方法进行解析(采用了反射机制,代码更精简):
gson.fromJson(String json,Class<T> cls)
gson.fromJson(String json,Type t)
同样,我们就上面四种类型的json格式分别进行解析,并封装的javabean对象中:
public static <T> T getBean(String json,Class<T> cls)
{
T t = null;
try
{
Gson gson = new Gson();
t = gson.fromJson(json, cls);
} catch (Exception e)
{
e.printStackTrace();
}
return t;
}
public static List<Person> getPersons(String json)
{
List<Person> list = null;
try
{
Gson gson = new Gson();
TypeToken<List<Person>> typeToken = new TypeToken<List<Person>>(){};
list = gson.fromJson(json,typeToken.getType());
} catch (Exception e)
{
e.printStackTrace();
}
return list;
}
public static List<String> getPersonNames(String json)
{
Log.i(TAG,"RUN3...");
List<String> list = new ArrayList<String>();
try
{
Gson gson = new Gson();
list = gson.fromJson(json,new TypeToken<List<String>>(){}.getType());
} catch (Exception e)
{
e.printStackTrace();
}
return list;
}
public static List<Map<String,String>> getPersonNameJobs(String json)
{
Log.i(TAG,"RUN4...");
List<Map<String,String>> list = null;
try
{
Gson gson = new Gson();
list = gson.fromJson(json,new TypeToken<List<Map<String,String>>>(){}.getType());
} catch (Exception e)
{
e.printStackTrace();
}
return list;
}
大家可能注意到我们使用了TypeToken类,这个类可以用来获取我们要反射的类型。那为什么要new一个匿名内部类呢?
之前看过一个视频上说的是TypeToken是抽象类,但是打开源码发现,该类并不是抽象类!
之所以new一个匿名内部类,是因为该类的的构造器是protected的!故在其他包中不能new实例,故需创建一个子类继承TypeToken,然后new子类的实例。
源码:
public class TypeToken<T> {
final Class<? super T> rawType;
final Type type;
final int hashCode;
/**
* Constructs a new type literal. Derives represented class from type
* parameter.
*
* <p>Clients create an empty anonymous subclass. Doing so embeds the type
* parameter in the anonymous class's type hierarchy so we can reconstitute it
* at runtime despite erasure.
*/
@SuppressWarnings("unchecked")
protected TypeToken() {
this.type = getSuperclassTypeParameter(getClass());
this.rawType = (Class<? super T>) $Gson$Types.getRawType(type);
this.hashCode = type.hashCode();
}
...