当前位置:   article > 正文

Android:解析JSON的三种方式_androidparseobject方法

androidparseobject方法

       什么是Json?

      Json(Javascript Object Notation):Javascript对象表示法。是一种轻量级的数据交换格式,相比于xml这种数据交换格式来说,因为解析xml比较的复杂,而且需要编写大段的代码,所以客户端和服务器的数据交换格式往往通过Json来进行交换。

     Json一共有两种数据结构:

     1、一种是以 (key/value)对形式存在的无序的jsonObject对象,一个对象以“{”(左花括号)开始,“}”(右花括号)结束。每个“名称”后跟一个“:”(冒号);“‘名称/值’ 对”之间使用“,”(逗号)分隔。

     2、另一种数据格式就是有序的value的集合,这种形式被称为是jsonArray集合,数组是值(value)的有序集合。一个数组以“[”(左中括号)开始,“]”(右中括号)结束。值之间使用“,”(逗号)分隔。

          {}双括号表示对象;

          []中括号表示数组;

          " " 双引号内是属性或值;

           : 冒号表示后者是前者的值(这个值可以是字符串、数字、也可以是另一个数组或对象);

所以 {"name": "Michael"} 可以理解为是一个包含name为Michael的对象;

而[{"name": "Michael"},{"name": "Jerry"}]就表示包含两个对象的数组。
当然了,你也可以使用{"name":["Michael","Jerry"]}来简化上面一部,这是一个拥有一个name数组的对象。

     

   下面通过解析Json的三种方式来实现在Android客户端和服务器端使用json这种数据格式来进行数据的交换。

一、解析JSON之使用原生态解析


    Android客户端通过一个AsyncTask异步任务请求服务器端的某些数据,AsyncTask两个方法(1)获取网络数据:doInBackground();(2)更新UI(数据):onPostExecute()。在解析完这些数据后,onPostExecute()方法会将解析的数据内容更新到适配器,通知适配器发送改变。代码注释如下:

  1. public class JsonActivity extends AppCompatActivity {
  2. private ListView lv_main_jsondata;
  3. private List<UserEntity> list=new ArrayList<>();//定义一个对象集合
  4. private ProgressDialog progress;
  5. private JsonActivity.myAdapter myAdapter;
  6. @Override
  7. protected void onCreate(Bundle savedInstanceState) {
  8. super.onCreate(savedInstanceState);
  9. setContentView(R.layout.activity_json);
  10. lv_main_jsondata = (ListView) findViewById(R.id.lv_main_jsondata);//获取listview控件
  11. myAdapter = new myAdapter();//实列化对象
  12. //给listview一个适配器,需要自己写一个类继承BaseAdapter
  13. lv_main_jsondata.setAdapter(myAdapter);
  14. //增加动画加载效果
  15. progress = new ProgressDialog(this);
  16. progress.setMessage("locating.....");//获取动画加载消息内容
  17. }
  18. //1、写一个类继承BaseAdapter,重写它的四个方法
  19. class myAdapter extends BaseAdapter{
  20. @Override
  21. public int getCount() {//获取总数量
  22. return list.size();
  23. }
  24. @Override
  25. public Object getItem(int position) {//获取当前位置
  26. return list.get(position);
  27. }
  28. @Override
  29. public long getItemId(int position) {//获取当前位置的ID
  30. return position;
  31. }
  32. @Override
  33. public View getView(int position, View convertView, ViewGroup parent) {//获取视图
  34. if (convertView==null){
  35. convertView= LayoutInflater.from(JsonActivity.this).inflate(R.layout.dom_listview,null);
  36. DomActivity activity=new DomActivity();//实列化一个对象
  37. //将对象的属性增加到相对应的控件中
  38. activity.uname= (TextView) convertView.findViewById(R.id.tv_listview_one);
  39. activity.content= (TextView) convertView.findViewById(R.id.tv_listview_two);
  40. activity.anthour= (TextView) convertView.findViewById(R.id.tv_listview_three);
  41. convertView.setTag(activity);//获取标签
  42. }
  43. DomActivity domActivity= (DomActivity) convertView.getTag();//通过convertView得到标签
  44. //获取对象的属性,将每个属性增加到它相对应的位置
  45. domActivity.uname.setText(list.get(position).getUname());
  46. domActivity.content.setText(list.get(position).getContent());
  47. domActivity.anthour.setText(list.get(position).getAnthour());
  48. return convertView;
  49. }
  50. }
  51. //获取Json数据
  52. public void getjson(View view){
  53. progress.show();//更新数据之前增加动画加载
  54. new myTask().execute();
  55. }
  56. //1、写一个类继承AsyncTask,重写它的两个方法
  57. // <1、获取网络数据:doInBackground
  58. // <2、更新UI(数据):onPostExecute
  59. class myTask extends AsyncTask{
  60. private StringBuffer stringBuffer;
  61. //获取网络数据:doInBackground
  62. @Override
  63. protected Object doInBackground(Object[] params) {
  64. //(1)、获得数据路径
  65. String path=getString(R.string.path)+"android_json.xhtml";
  66. try {
  67. //(2)、实例化url:将获取网络数据的路径放到URL中。
  68. URL url=new URL(path);
  69. //(3)/通过URL获取连接的对象
  70. HttpURLConnection httpURLConnection= (HttpURLConnection) url.openConnection();
  71. //(4)、设置参数 01请求的方式:1、get;2、post; 02设置请求时间
  72. httpURLConnection.setRequestMethod("GET");
  73. httpURLConnection.setConnectTimeout(5000);
  74. //(5)、判断响应码是否是200 是的话就请求到数据
  75. if (httpURLConnection.getResponseCode()==200){//如果请求到的响应码是200 那么就要去读取它的数据
  76. InputStream inputStream=httpURLConnection.getInputStream();//以字节流的形式得到数据
  77. //通过字符流(bufferedread)的形式读取数据
  78. BufferedReader bufferedReader=new BufferedReader(new InputStreamReader(inputStream));//将字符流转成字节流
  79. //实列化一个对象
  80. stringBuffer = new StringBuffer();
  81. String str=null;//定义一个接收的字符串
  82. while((str=bufferedReader.readLine())!=null){//字符流读取数据不为空
  83. stringBuffer.append(str);//把字符流读取的数据增加到对象中
  84. }
  85. Log.i("test", "doInBackground: "+ stringBuffer.toString());
  86. }
  87. //解析JSON
  88. try {
  89. // 一、使用原生态解析
  90. //1、通过jsonobject对象获取数据
  91. JSONObject jsonObject=new JSONObject(stringBuffer.toString());
  92. //2、获取数据的属性
  93. String clazz=jsonObject.getString("class");
  94. Log.i("test", "doInBackground: "+clazz);
  95. int munber=jsonObject.getInt("lists");//获取它的数量
  96. Log.i("test", "doInBackground: "+munber);
  97. //3、获取集合的属性
  98. JSONArray array= jsonObject.getJSONArray("fqs");
  99. for (int i = 0; i <array.length() ; i++) {//循环获取array的长度
  100. JSONObject object= array.getJSONObject(i);//拿到每一个对象
  101. //通过对象获取每个属性
  102. String name=object.getString("name");
  103. String content=object.getString("content");
  104. String anthour=object.getString("anthour");
  105. UserEntity user=new UserEntity(name,content,anthour);//实列化一个对象,每循环一次实列化一次
  106. list.add(user);
  107. }
  108. } catch (JSONException e) {
  109. e.printStackTrace();
  110. }
  111. } catch (MalformedURLException e) {
  112. e.printStackTrace();
  113. } catch (IOException e) {
  114. e.printStackTrace();
  115. }
  116. return null;
  117. }
  118. //更新UI(数据):onPostExecute
  119. @Override
  120. protected void onPostExecute(Object o) {
  121. myAdapter.notifyDataSetChanged();//通知适配器数据发生改变
  122. progress.cancel();//动画取消
  123. super.onPostExecute(o);
  124. }
  125. }
  126. }

二、解析JSON之GSON解析


   使用Gson解析需要去下载Gson这个jar包,导入到我们的项目中。用Gson,我们可以非常轻松的实现数据对象和json对象的相互转化,其中我们最常用的方法fromJSON(),将json对象转换成我们需要的数据对象。代码注释如下:

  1. public class JsonActivity extends AppCompatActivity {
  2. private ListView lv_main_jsondata;
  3. private List<UserEntity> list=new ArrayList<>();//定义一个对象集合
  4. private ProgressDialog progress;
  5. private JsonActivity.myAdapter myAdapter;
  6. @Override
  7. protected void onCreate(Bundle savedInstanceState) {
  8. super.onCreate(savedInstanceState);
  9. setContentView(R.layout.activity_json);
  10. lv_main_jsondata = (ListView) findViewById(R.id.lv_main_jsondata);//获取listview控件
  11. myAdapter = new myAdapter();//实列化对象
  12. //给listview一个适配器,需要自己写一个类继承BaseAdapter
  13. lv_main_jsondata.setAdapter(myAdapter);
  14. //增加动画加载效果
  15. progress = new ProgressDialog(this);
  16. progress.setMessage("locating.....");//获取动画加载消息内容
  17. }
  18. //1、写一个类继承BaseAdapter,重写它的四个方法
  19. class myAdapter extends BaseAdapter{
  20. @Override
  21. public int getCount() {//获取总数量
  22. return list.size();
  23. }
  24. @Override
  25. public Object getItem(int position) {//获取当前位置
  26. return list.get(position);
  27. }
  28. @Override
  29. public long getItemId(int position) {//获取当前位置的ID
  30. return position;
  31. }
  32. @Override
  33. public View getView(int position, View convertView, ViewGroup parent) {//获取视图
  34. if (convertView==null){
  35. convertView= LayoutInflater.from(JsonActivity.this).inflate(R.layout.dom_listview,null);
  36. DomActivity activity=new DomActivity();//实列化一个对象
  37. //将对象的属性增加到相对应的控件中
  38. activity.uname= (TextView) convertView.findViewById(R.id.tv_listview_one);
  39. activity.content= (TextView) convertView.findViewById(R.id.tv_listview_two);
  40. activity.anthour= (TextView) convertView.findViewById(R.id.tv_listview_three);
  41. convertView.setTag(activity);//获取标签
  42. }
  43. DomActivity domActivity= (DomActivity) convertView.getTag();//通过convertView得到标签
  44. //获取对象的属性,将每个属性增加到它相对应的位置
  45. domActivity.uname.setText(list.get(position).getUname());
  46. domActivity.content.setText(list.get(position).getContent());
  47. domActivity.anthour.setText(list.get(position).getAnthour());
  48. return convertView;
  49. }
  50. }
  51. //获取Json数据
  52. public void getjson(View view){
  53. progress.show();//更新数据之前增加动画加载
  54. new myTask().execute();
  55. }
  56. //1、写一个类继承AsyncTask,重写它的两个方法
  57. // <1、获取网络数据:doInBackground
  58. // <2、更新UI(数据):onPostExecute
  59. class myTask extends AsyncTask{
  60. private StringBuffer stringBuffer;
  61. //获取网络数据:doInBackground
  62. @Override
  63. protected Object doInBackground(Object[] params) {
  64. //(1)、获得数据路径
  65. String path=getString(R.string.path)+"android_json.xhtml";
  66. try {
  67. //(2)、实例化url:将获取网络数据的路径放到URL中。
  68. URL url=new URL(path);
  69. //(3)/通过URL获取连接的对象
  70. HttpURLConnection httpURLConnection= (HttpURLConnection) url.openConnection();
  71. //(4)、设置参数 01请求的方式:1、get;2、post; 02设置请求时间
  72. httpURLConnection.setRequestMethod("GET");
  73. httpURLConnection.setConnectTimeout(5000);
  74. //(5)、判断响应码是否是200 是的话就请求到数据
  75. if (httpURLConnection.getResponseCode()==200){//如果请求到的响应码是200 那么就要去读取它的数据
  76. InputStream inputStream=httpURLConnection.getInputStream();//以字节流的形式得到数据
  77. //通过字符流(bufferedread)的形式读取数据
  78. BufferedReader bufferedReader=new BufferedReader(new InputStreamReader(inputStream));//将字符流转成字节流
  79. //实列化一个对象
  80. stringBuffer = new StringBuffer();
  81. String str=null;//定义一个接收的字符串
  82. while((str=bufferedReader.readLine())!=null){//字符流读取数据不为空
  83. stringBuffer.append(str);//把字符流读取的数据增加到对象中
  84. }
  85. Log.i("test", "doInBackground: "+ stringBuffer.toString());
  86. }
  87. //解析JSON
  88. //二、使用Gson解析Json
  89. Gson gson=new Gson();//实列化一个对象
  90. //通过gson解析一个对象,将buffered流解析到a对象中
  91. BigjsonActivity bjson=gson.fromJson(stringBuffer.toString(),BigjsonActivity.class);
  92. //通过对象获取这个对象中相对应的属性
  93. String clazz=bjson.getClazz();
  94. int munber=bjson.getLists();
  95. Log.i("test", "doInBackground: "+clazz+" ;"+munber);
  96. list.addAll(bjson.getListuser());//将对象中的集合放入list对象集合中
  97. } catch (MalformedURLException e) {
  98. e.printStackTrace();
  99. } catch (IOException e) {
  100. e.printStackTrace();
  101. }
  102. return null;
  103. }
  104. //更新UI(数据):onPostExecute
  105. @Override
  106. protected void onPostExecute(Object o) {
  107. myAdapter.notifyDataSetChanged();//通知适配器数据发生改变
  108. progress.cancel();//动画取消
  109. super.onPostExecute(o);
  110. }
  111. }
  112. }
三、解析JSON之FastJson解析


       使用FastJson需要导入第三方包,用法和Gson一样,实现数据对象和json对象的相互转化Gson是用fromJSON()方法,而FastJson用JSON.parseObject()方法,然后将json对象中的集合放入我们需要的数据对象集合中。代码注释如下:

  1. public class JsonActivity extends AppCompatActivity {
  2. private ListView lv_main_jsondata;
  3. private List<UserEntity> list=new ArrayList<>();//定义一个对象集合
  4. private ProgressDialog progress;
  5. private JsonActivity.myAdapter myAdapter;
  6. @Override
  7. protected void onCreate(Bundle savedInstanceState) {
  8. super.onCreate(savedInstanceState);
  9. setContentView(R.layout.activity_json);
  10. lv_main_jsondata = (ListView) findViewById(R.id.lv_main_jsondata);//获取listview控件
  11. myAdapter = new myAdapter();//实列化对象
  12. //给listview一个适配器,需要自己写一个类继承BaseAdapter
  13. lv_main_jsondata.setAdapter(myAdapter);
  14. //增加动画加载效果
  15. progress = new ProgressDialog(this);
  16. progress.setMessage("locating.....");//获取动画加载消息内容
  17. }
  18. //1、写一个类继承BaseAdapter,重写它的四个方法
  19. class myAdapter extends BaseAdapter{
  20. @Override
  21. public int getCount() {//获取总数量
  22. return list.size();
  23. }
  24. @Override
  25. public Object getItem(int position) {//获取当前位置
  26. return list.get(position);
  27. }
  28. @Override
  29. public long getItemId(int position) {//获取当前位置的ID
  30. return position;
  31. }
  32. @Override
  33. public View getView(int position, View convertView, ViewGroup parent) {//获取视图
  34. if (convertView==null){
  35. convertView= LayoutInflater.from(JsonActivity.this).inflate(R.layout.dom_listview,null);
  36. DomActivity activity=new DomActivity();//实列化一个对象
  37. //将对象的属性增加到相对应的控件中
  38. activity.uname= (TextView) convertView.findViewById(R.id.tv_listview_one);
  39. activity.content= (TextView) convertView.findViewById(R.id.tv_listview_two);
  40. activity.anthour= (TextView) convertView.findViewById(R.id.tv_listview_three);
  41. convertView.setTag(activity);//获取标签
  42. }
  43. DomActivity domActivity= (DomActivity) convertView.getTag();//通过convertView得到标签
  44. //获取对象的属性,将每个属性增加到它相对应的位置
  45. domActivity.uname.setText(list.get(position).getUname());
  46. domActivity.content.setText(list.get(position).getContent());
  47. domActivity.anthour.setText(list.get(position).getAnthour());
  48. return convertView;
  49. }
  50. }
  51. //获取Json数据
  52. public void getjson(View view){
  53. progress.show();//更新数据之前增加动画加载
  54. new myTask().execute();
  55. }
  56. //1、写一个类继承AsyncTask,重写它的两个方法
  57. // <1、获取网络数据:doInBackground
  58. // <2、更新UI(数据):onPostExecute
  59. class myTask extends AsyncTask{
  60. private StringBuffer stringBuffer;
  61. //获取网络数据:doInBackground
  62. @Override
  63. protected Object doInBackground(Object[] params) {
  64. //(1)、获得数据路径
  65. String path=getString(R.string.path)+"android_json.xhtml";
  66. try {
  67. //(2)、实例化url:将获取网络数据的路径放到URL中。
  68. URL url=new URL(path);
  69. //(3)/通过URL获取连接的对象
  70. HttpURLConnection httpURLConnection= (HttpURLConnection) url.openConnection();
  71. //(4)、设置参数 01请求的方式:1、get;2、post; 02设置请求时间
  72. httpURLConnection.setRequestMethod("GET");
  73. httpURLConnection.setConnectTimeout(5000);
  74. //(5)、判断响应码是否是200 是的话就请求到数据
  75. if (httpURLConnection.getResponseCode()==200){//如果请求到的响应码是200 那么就要去读取它的数据
  76. InputStream inputStream=httpURLConnection.getInputStream();//以字节流的形式得到数据
  77. //通过字符流(bufferedread)的形式读取数据
  78. BufferedReader bufferedReader=new BufferedReader(new InputStreamReader(inputStream));//将字符流转成字节流
  79. //实列化一个对象
  80. stringBuffer = new StringBuffer();
  81. String str=null;//定义一个接收的字符串
  82. while((str=bufferedReader.readLine())!=null){//字符流读取数据不为空
  83. stringBuffer.append(str);//把字符流读取的数据增加到对象中
  84. }
  85. Log.i("test", "doInBackground: "+ stringBuffer.toString());
  86. }
  87. //解析JSON
  88. //三、使用FsatJson解析
  89. //通过json解析一个对象,将buffered流解析到对象中
  90. BigjsonActivity bjson =JSON.parseObject(stringBuffer.toString(),BigjsonActivity.class);
  91. //通过对象获取这个对象中相对应的属性
  92. String clazz=bjson.getClazz();
  93. int munber=bjson.getLists();
  94. Log.i("test", "doInBackground: "+clazz+" ;"+munber);
  95. list.addAll(bjson.getFqs());//将对象中的集合放入list对象集合中
  96. } catch (MalformedURLException e) {
  97. e.printStackTrace();
  98. } catch (IOException e) {
  99. e.printStackTrace();
  100. }
  101. return null;
  102. }
  103. //更新UI(数据):onPostExecute
  104. @Override
  105. protected void onPostExecute(Object o) {
  106. myAdapter.notifyDataSetChanged();//通知适配器数据发生改变
  107. progress.cancel();//动画取消
  108. super.onPostExecute(o);
  109. }
  110. }
  111. }
    总结:

      JSON对于移动设备来说,尤其对于网络环境较差和流量限制的情况下,相对于XML格式的数据传输会更节省流量,传输效率更高。在这三种解析方式中FastJson是效率最高的。

      Android的JSON解析部分都在包org.json下,主要有以下几个类:

《1、JSONObject:可以看作是一个json对象,这是系统中有关JSON定义的基本单元,其包含一对儿(Key/Value)数值。它对外部(External:应用toString()方法输出的数值)调用的响应体现为一个标准的字符串(例如:{"JSON": "Hello, World"},最外被大括号包裹,其中的Key和Value被冒号":"分隔)。其对于内部(Internal)行为的操作格式略微,例如:初始化一个JSONObject实例,引用内部的put()方法添加数值:new JSONObject().put("JSON", "Hello, World!"),在Key和Value之间是以逗号","分隔。Value的类型包括:Boolean、JSONArray、JSONObject、Number、String或者默认值JSONObject.NULL object。
《2、JSONStringer:json文本构建类 ,根据官方的解释,这个类可以帮助快速和便捷的创建JSON text。其最大的优点在于可以减少由于 格式的错误导致程序异常,引用这个类可以自动严格按照JSON语法规则(syntax rules)创建JSON text。每个JSONStringer实体只能对应创建一个JSON text。。其最大的优点在于可以减少由于格式的错误导致程序异常,引用这个类可以自动严格按照JSON语法规则(syntax rules)创建JSON text。每个JSONStringer实体只能对应创建一个JSON text。
《3、JSONArray:它代表一组有序的数值。将其转换为String输出(toString)所表现的形式是用方括号包裹,数值以逗号”,”分隔(例如:[value1,value2,value3],大家可以亲自利用简短的代码更加直观的了解其格式)。这个类的内部同样具有查询行为,get()和opt()两种方法都可以通过index索引返回指定的数值,put()方法用来添加或者替换数值。同样这个类的value类型可以包括:Boolean、JSONArray、JSONObject、Number、String或者默认JSONObject.NULL object。
《4、JSONTokener:json解析类。

《5、JSONException:json中用到的异常

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/weixin_40725706/article/detail/245914
推荐阅读
相关标签
  

闽ICP备14008679号