android JSONObject的使用


今天,简单讲讲android里如何使用


JSONObject。


昨天,自己使用JSONObject构造json数据时,居然发现构造6个之后,json数据就没有构造进json的括号里,当时是用Debug进行调试,所以百思不得其解。在网上查了资料,也没有明白,后来发现用log打印的json数据是正确的,是debug显示的问题。所以这里还是记录一下JSONObject的使用,避免以后出现这样的问题。


Android之JSON全面解析与使用

什么是JSON

  • JSON 指的是 JavaScript 对象表示法(JavaScript Object Notation)
  • JSON 是轻量级的文本数据交换格式
  • JSON 独立于语言 (单纯的数据格式,不受语言的约束)
  • JSON 具有自我描述性,更易理解


对于JSON的定义以及数据格式,没有什么太多的难点,这里为官网对JSON的定义。从官网描述中可以看出,JSON本身是JavaScript中对象的描述格式,后来得以推广并逐渐取代xml。

JSON和XML的比较

相比 XML 的不同之处

  • 没有结束标签(类似于键值对的形式)
  • 更短(没有结束标签,当然短了)
  • 读写的速度更快
  • 能够使用内建的 JavaScript eval() 方法进行解析
  • 使用数组
  • 不使用保留字


原生JSON解析

Android原生的解析实际上使用的JSON的一个官方jar包。对于JSON,不需要页面展示,所以使用intellij idea进行演示。

在使用之前我们需要下载org.json的jar包。对于Android 开发环境不需要下载此jar包。因为Android SDK 中已经默认包含了该jar包。

json jar 下载地址

下载完之后导入即可。

JSONObject对象解析

下面看一下数据

{
    "user":{
        "name":"alex",
        "age":"18",
        "isMan":true
    }
}


有一个user字段,其中包含了该user的一些基本属性。那么如何解析呢?

在解析时,有一个很关键的地方:如果是{}包含,则为JSONObject对象,如果为[]则为JSONArray对象。

看到上面的例子,我们看到整个数据为JSONObject,其内部包含了一个user字段,该字段的值也是一个JSONObject对象。

public class OrgJSONTest {

    public static String json = "{\"user\":{\"name\":\"alex\",\"age\":\"18\",\"isMan\":true}}";


    public static void main(String[] args){
        JSONObject obj = new JSONObject(json);//最外层的JSONObject对象
        JSONObject user = obj.getJSONObject("user");//通过user字段获取其所包含的JSONObject对象
        String name = user.getString("name");//通过name字段获取其所包含的字符串

        System.out.println(name);


    }
}


打印结果如下

alex

可以看到获取到了相应的值。

JSONObject对象中封装了getXXX()等一系列方法。用以获取字符串,整形等等一系列的值。

对于如上例子,完全解析user对象如下

       String name = user.getString("name");//通过name字段获取其所包含的字符串
        String age = user.getString("age");
        boolean isMan = user.getBoolean("isMan");

        System.out.println("name:"+name+"\nage:"+age+"\nisMan:"+isMan);


结果如下

name:alex
age:18
isMan:true


这种通过getXXX的方式,无疑会出现一些问题,我们开始一一尝试。

getXXX方法获取的类型不符
  • 字符串类型转整形

对于上面的例子,我们可以看到age字段虽然其对应的值是双引号括起的字符串,但其实际上是一个整形,那么我们是否能够通过getInt获取整形呢。

  int age = user.getInt("age");

   age:18


当然是可以得,同时字符串类型可以转化为布尔类型,整数类型,浮点型等等。但字符串的内容必须符合规范,否则会报异常。如果看其源码可知,其内部实质是调用了对应对象的parseXXX()方法进行转化操作。

    //getInt源码
  public int getInt(String key) throws JSONException {
        Object object = this.get(key);

        try {
            //关键点,如果是数值类型,则调用intValue(),否则强转成字符串之后调用parserInt方法()
            return object instanceof Number?((Num,ber)object).intValue():Integer.parseInt((String)object);
        } catch (Exception var4) {
            throw new JSONException("JSONObject[" + quote(key) + "] is not an int.");
        }
    }


  • 整形等转字符串类型

    按照如上的思维逻辑,直接getString("xxx")就可以了。但事实正好相反,该方法,如果对应值不是双引号括起的,则会抛出异常。

     //getString 源码
     public String getString(String key) throws JSONException {
            Object object = this.get(key);
            //直接判断是否是字符串类型,如果不是,则抛出异常
            if(object instanceof String) {
                return (String)object;
            } else {
                throw new JSONException("JSONObject[" + quote(key) + "] not a string.");
            }
        }
    


    getXXX(“”) 没有对应的键值

    通过上面的例子,可以得知getXXX("")方法是通过字段(键)获取对应的值。那么肯定存在一种情况,及没有键的存在。

    System.out.println(user.getString("sex"));

    Exception in thread "main" org.json.JSONException: JSONObject["sex"] not found.
        at org.json.JSONObject.get(JSONObject.java:471)
        at org.json.JSONObject.getString(JSONObject.java:717)
        at json.OrgJSONTest.main(OrgJSONTest.java:24)


    果断报异常。

    那么怎么办呢:使用optXXX()。


    这里简单讲解了JSONObject解析字符串,下面具体举一个例子:

    实验要求,创建以下的JSON数据并对其进行解析显示到TextView组件中:

    {
        "cat":"it",
        "languages":[
            {"id":1,"ide":"Eclipse","name":"Java"},
            {"id":2,"ide":"XCode","name":"Swift"},
            {"id":3,"ide":"Visual Studio","name":"C#"}
        ]
    }



    下面先创建一个空的项目,然对activity_main.xml和MainActivity.java进行编辑

    activity_main.xml代码:

    <?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:tools="http://schemas.android.com/tools"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical"
        tools:context="com.oak.d4_json.MainActivity">
    
        <Button
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="创建"
            android:id="@+id/bt_create"/>
        <Button
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="读取"
            android:id="@+id/bt_read"/>
        <TextView
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:id="@+id/tv"/>
    </LinearLayout>
    


    MainActivity.java代码:

    package com.oak.d4_json;
    
    import android.os.Bundle;
    import android.support.v7.app.AppCompatActivity;
    import android.view.View;
    import android.widget.Button;
    import android.widget.TextView;
    import android.widget.Toast;
    
    import org.json.JSONArray;
    import org.json.JSONException;
    import org.json.JSONObject;
    
    import java.io.BufferedReader;
    import java.io.File;
    import java.io.FileInputStream;
    import java.io.FileNotFoundException;
    import java.io.FileOutputStream;
    import java.io.IOException;
    import java.io.InputStreamReader;
    import java.io.UnsupportedEncodingException;
    
    public class MainActivity extends AppCompatActivity {
        private Button bt_create;//声明创建按钮组件变量
        private Button bt_read;//声明读取按钮组件变量
        private File file;//声明一个文件对象
        private TextView tv;//声明TextView组件变量
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
            bt_create = (Button) findViewById(R.id.bt_create);//获取到创建按钮组件
            bt_read = (Button) findViewById(R.id.bt_read);//获取到读取按钮组件
            tv = (TextView) findViewById(R.id.tv);//获取到TextView组件
    
            file = new File(getFilesDir(),"Test.json");//获取到应用在内部的私有文件夹下对应的Test.json文件
            bt_create.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View view) {
                    try {
                        JSONObject root = new JSONObject();//实例一个JSONObject对象
                        root.put("cat","it");//对其添加一个数据
    
                        JSONArray languages = new JSONArray();//实例一个JSON数组
                        JSONObject lan1 = new JSONObject();//实例一个lan1的JSON对象
                        lan1.put("id",1);//对lan1对象添加数据
                        lan1.put("ide","Eclipse");//对lan1对象添加数据
                        lan1.put("name","Java");//对lan1对象添加数据
                        JSONObject lan2 = new JSONObject();//实例一个lan2的JSON对象
                        lan2.put("id",2);//对lan2对象添加数据
                        lan2.put("ide","XCode");//对lan2对象添加数据
                        lan2.put("name","Swift");//对lan2对象添加数据
                        JSONObject lan3 = new JSONObject();//实例一个lan3的JSON对象
                        lan3.put("id",3);//对lan3对象添加数据
                        lan3.put("ide","Visual Studio");//对lan3对象添加数据
                        lan3.put("name","C#");//对lan3对象添加数据
                        languages.put(0,lan1);//将lan1对象添加到JSON数组中去,角标为0
                        languages.put(1,lan2);//将lan2对象添加到JSON数组中去,角标为1
                        languages.put(2,lan3);//将lan3对象添加到JSON数组中去,角标为2
    
                        root.put("languages",languages);//然后将JSON数组添加到名为root的JSON对象中去
    
                        FileOutputStream fos = new FileOutputStream(file);//创建一个文件输出流
                        fos.write(root.toString().getBytes());//将生成的JSON数据写出
                        fos.close();//关闭输出流
                        Toast.makeText(getApplicationContext(),"创建成功!",Toast.LENGTH_SHORT).show();
                    } catch (JSONException e) {
                        e.printStackTrace();
                    } catch (FileNotFoundException e) {
                        e.printStackTrace();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            });
            bt_read.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View view) {
                    try {
                        FileInputStream fis = new FileInputStream(file);//获取一个文件输入流
                        InputStreamReader isr = new InputStreamReader(fis);//读取文件内容
                        BufferedReader bf = new BufferedReader(isr);//将字符流放入缓存中
                        String line;//定义一个用来临时保存数据的变量
                        StringBuilder sb = new StringBuilder();//实例化一个字符串序列化
                        while((line = bf.readLine()) != null){
                                sb.append(line);//将数据添加到字符串序列化中
                        }
                        //关闭流
                        fis.close();
                        isr.close();
                        bf.close();
                        JSONObject root = new JSONObject(sb.toString());//用JSONObject进行解析
                        String cat = root.getString("cat");//获取字符串类型的键值对
                        tv.append("cat"+"="+cat+"\n");//显示数据
                        tv.append("---------------"+"\n");//分割线
                        JSONArray array = root.getJSONArray("languages");//获取JSON数据中的数组数据
                        for (int i=0; i<array.length(); i++){
                            JSONObject object = array.getJSONObject(i);//遍历得到数组中的各个对象
                            int id = object.getInt("id");//获取第一个值
                            String ide = object.getString("ide");//获取第二个值
                            String name = object.getString("name");//获取第三个值
                            tv.append("id"+"="+id+"\n");//显示数据
                            tv.append("ide"+"="+ide+"\n");//显示数据
                            tv.append("name"+"="+name+"\n");//显示数据
                            tv.append("---------------"+"\n");//分割线
                        }
                    } catch (FileNotFoundException e) {
                        e.printStackTrace();
                    } catch (UnsupportedEncodingException e) {
                        e.printStackTrace();
                    } catch (IOException e) {
                        e.printStackTrace();
                    } catch (JSONException e) {
                        e.printStackTrace();
                    }
    
    
                }
            });
        }
    }
    



    android JSONObject的使用就讲完了。


    就这么简单。

  • 11
    点赞
  • 44
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值