前言
上一篇博客已经介绍了在.Net下如何把对象序列化成Json字符串和Json数据的格式。如果不清楚的朋友可以过去看看:。这篇博客就来聊聊在Android平台下如何解析Json数据。
org.json
我们知道,Json有两种格式,键值对和数组,而Android对于Json的支持源于org.json包下的几个类。org.json下一共有四个类,但是经常使用的也就是两个类,分别对应了键值对和数组:JSONObject、JSONArray,弄清楚这两个类,基本上就了解了在Android下解析Json的方式。
对于这两个类的选择使用,其实可以简单的区分,如果是被包括在方括号"[]"内的Json数据,则使用JSONArray对象存放数据。如果是被包括在花括号"{}"内的Json数据,则使用JSONObject对象存放数据。
如上图,对于上面这个Json数据,解析的思路是先使用JSONArray解析Json数组,再遍历这个Json数组,使用JSONObject解析这个Json数组中的每个Json对象。
示例程序
JSONObject、JSONArray提供了一系列getXxx()的方法,获取其内部的值。下面就通过一个例子来讲解一下Android应用程序中解析Json的方法。
这个例子模拟现实情况,访问IIS上一个一般处理程序,通过不同的GET参数,返回不同的Json数据,具体数据的返回情况参见上一篇博客。
在此示例中展示解析四种数据的方式:
- Person:{"age":24,"id":20,"name":"slive"}
- List<Person>:[{"age":24,"id":20,"name":"slive"},{"age":34,"id":30,"name":"jack"},{"age":54,"id":40,"name":"damon"}]
- List<string>:["jack","dick","sean"]
- List<Map<String,Object>>:[[{"Key":"id","Value":17},{"Key":"name","Value":"jerry"},{"Key":"age","Value":24}],[{"Key":"id","Value":18},{"Key":"name","Value":"meimei"},{"Key":"age","Value":23}],[{"Key":"id","Value":19},{"Key":"name","Value":"damon"},{"Key":"age","Value":28}]]
从IIS上获取Json数据的方法,在另外一篇博客中有介绍:。这里方便大家查看:
1 package cn.bgxt.http; 2 3 import java.io.ByteArrayOutputStream; 4 import java.io.IOException; 5 import java.io.InputStream; 6 import java.net.HttpURLConnection; 7 import java.net.URL; 8 import android.util.Log; 9 10 public class HttpUtils {11 public HttpUtils() {12 // TODO Auto-generated constructor stub13 } 14 public static String getJsonContent(String url_path)15 {16 try {17 URL url=new URL(url_path);18 HttpURLConnection connection=(HttpURLConnection)url.openConnection();19 connection.setConnectTimeout(3000);20 connection.setRequestMethod("GET");21 connection.setDoInput(true);22 int code=connection.getResponseCode();23 if(200==code)24 {25 return changeJsonString(connection.getInputStream());26 }27 } catch (Exception e) {28 // TODO: handle exception29 Log.i("main", e.getMessage());30 }31 return null;32 }33 34 private static String changeJsonString(InputStream inputStream) {35 String jsonString="";36 try { 37 ByteArrayOutputStream outputStream=new ByteArrayOutputStream();38 int len=0;39 byte[] data=new byte[1024];40 while((len=inputStream.read(data))!=-1)41 {42 outputStream.write(data,0,len);43 }44 jsonString=new String(outputStream.toByteArray());45 } catch (IOException e) {46 // TODO Auto-generated catch block47 e.printStackTrace();48 }49 return jsonString;50 }51 }
从IIS上获取到Json数据之后,需要新建一个类来解析服务端获取到的Json数据:
1 package cn.bgxt.jsonUtils; 2 3 import java.util.ArrayList; 4 import java.util.HashMap; 5 import java.util.List; 6 import java.util.Map; 7 8 import org.json.JSONArray; 9 import org.json.JSONObject; 10 11 import cn.bgxt.domain.Person; 12 13 public class JsonTools { 14 15 public JsonTools() { 16 // TODO Auto-generated constructor stub 17 } 18 19 public static Person getPerson(String jsonString) 20 { 21 Person person=new Person(); 22 try { 23 //一个Json对象,使用JSONObject 24 JSONObject jsonObject=new JSONObject(jsonString); 25 //对JSONObject对象中直接以key的形式取其Value 26 person.setId(jsonObject.getInt("id")); 27 person.setName(jsonObject.getString("name")); 28 person.setAge(jsonObject.getInt("age")); 29 } catch (Exception e) { 30 // TODO: handle exception 31 } 32 return person; 33 } 34 35 public static ListgetPersonList(String jsonString) 36 { 37 List list=new ArrayList (); 38 try { 39 //最外层是一个数组[],所以使用JSONArray 40 JSONArray jsonarr=new JSONArray(jsonString); 41 Person person=null; 42 for(int i=0;i getStringList(String jsonString) 61 { 62 List list=new ArrayList (); 63 try { 64 JSONArray jsonArray=new JSONArray(jsonString); 65 for(int i =0;i > getMapList(String jsonString) 77 { 78 List
再就是在Activity中添加4个按钮,分别响应这四次解析,布局相对简单,仅四个按钮,此处不给出布局代码,有兴趣的可以下载源码查看。因为是Android4.0+的平台,所以不能在主线程中访问网络,需要另起线程,还有别忘记增加访问网络的权限。
Activity代码:
1 package cn.bgxt.jsonparser; 2 3 import java.util.List; 4 import java.util.Map; 5 6 import cn.bgxt.domain.Person; 7 import cn.bgxt.http.HttpUtils; 8 import cn.bgxt.jsonUtils.JsonTools; 9 import android.os.Bundle; 10 import android.app.Activity; 11 import android.util.Log; 12 import android.view.Menu; 13 import android.view.View; 14 import android.view.View.OnClickListener; 15 import android.widget.Button; 16 17 public class MainActivity extends Activity implements OnClickListener { 18 19 private String path_url = "http://192.168.1.106:1231/json/returnJson.ashx?JsonData="; 20 private Button person, personList, stringList, dicList; 21 private String path = ""; 22 23 @Override 24 protected void onCreate(Bundle savedInstanceState) { 25 super.onCreate(savedInstanceState); 26 setContentView(R.layout.activity_main); 27 28 person = (Button) findViewById(R.id.person); 29 personList = (Button) findViewById(R.id.personList); 30 stringList = (Button) findViewById(R.id.stringList); 31 dicList = (Button) findViewById(R.id.dicList); 32 person.setOnClickListener(this); 33 personList.setOnClickListener(this); 34 stringList.setOnClickListener(this); 35 dicList.setOnClickListener(this); 36 } 37 38 @Override 39 public boolean onCreateOptionsMenu(Menu menu) { 40 getMenuInflater().inflate(R.menu.main, menu); 41 return true; 42 } 43 44 @Override 45 public void onClick(View v) { 46 47 switch (v.getId()) { 48 case R.id.person: 49 Thread thread = new Thread(new Runnable() { 50 51 @Override 52 public void run() { 53 // TODO Auto-generated method stub 54 path = path_url + "Person"; 55 String jsonString = HttpUtils.getJsonContent(path); 56 Person person = JsonTools.getPerson(jsonString); 57 Log.i("main", person.toString()); 58 } 59 }); 60 thread.start(); 61 break; 62 case R.id.personList: 63 Thread thread1 = new Thread(new Runnable() { 64 @Override 65 public void run() { 66 // TODO Auto-generated method stub 67 path = path_url + "PersonList"; 68 String jsonString = HttpUtils.getJsonContent(path); 69 Listpersons = JsonTools.getPersonList(jsonString); 70 for(Person p:persons) 71 { 72 Log.i("main", p.toString()); 73 } 74 } 75 }); 76 thread1.start(); 77 break; 78 case R.id.stringList: 79 Thread thread2 = new Thread(new Runnable() { 80 @Override 81 public void run() { 82 // TODO Auto-generated method stub 83 path = path_url + "StringList"; 84 String jsonString = HttpUtils.getJsonContent(path); 85 List strings = JsonTools.getStringList(jsonString); 86 for(String s:strings) 87 { 88 Log.i("main", s); 89 } 90 } 91 }); 92 thread2.start(); 93 break; 94 case R.id.dicList: 95 Thread thread3 = new Thread(new Runnable() { 96 @Override 97 public void run() { 98 // TODO Auto-generated method stub 99 path = path_url + "DicList";100 String jsonString = HttpUtils.getJsonContent(path);101 List > maps = JsonTools.getMapList(jsonString);102 for(Map m:maps)103 {104 Log.i("main", m.toString());105 } 106 }107 });108 thread3.start();109 break;110 }111 112 }113 114 }
依次按顺序点击按钮,可以再LogCat中查看数据:
总结
本来Java中有一套自己的序列化办法,序列化出来的Json数据并不是如此的格式,可这里使用的.Net序列化的办法,但是参照本文的思想,只要知道Json的格式,无论Json数据变什么样子,都是可以解析出来的。真实的Android开发服务端的时候,还是尽量使用Java来开发,减少兼容性的问题。
请支持原创,尊重原创,转载请注明出处。谢谢。