发布时间:2025-12-09 13:58:40 浏览次数:4
在程序开发过程中,在参数传递,函数返回值等方面,越来越多的使用JSON。JSON(JavaScript Object Notation)是一种轻量级的数据交换格式,同时也易于机器解析和生成、易于理解、阅读和撰写,而且Json采用完全独立于语言的文本格式,这使得Json成为理想的数据交换语言。
JSON建构于两种结构:
JSON-lib是一个用于转换beans、maps、collections、java arrays、XML成JSON对象以及反之转化成benas和DynaBeans的java库。JSON-lib建立在Douglas Crockford的工作基础之上。
public final class JSONObject extends AbstractJSON implements JSON, Map, Comparable { 从上述的接口声明中,可以看到JSONObject实现了接口Map,Comparable,这两个接口为java jdk自带的接口,而JSON接口代码如下:
package net.sf.json;import java.io.Serializable;import java.io.Writer;public interface JSON extends Serializable { boolean isArray(); boolean isEmpty(); int size(); String toString(int var1); String toString(int var1, int var2); Writer write(Writer var1); }一个JSONObject是一个无序的name/value对集合。它的外部形式是一个由花括号“{}”括起的字符串,在name和value之间使用冒号“:”隔开,在names/values之间用逗号隔开。JSONObjet的图示如下:
如下例所示:
{ "errCode": 200, "msg": "success", "data": { "jguan": "11", "xming": "11", "dwei_name": "", "zji_code": "", "is_cbdwfzltxiu": "", "fzltxiu_date": "2", } }内部的形式是一个拥有get和opt方法来根据name访问value、put方法来根据name增加或替换value的对象。在JSONObject中,值可以为以下类型:
Boolean、 JSONObject、 JSONArray、 Number、 String、 或者JSONNull对象JSONObject类型的构造器可以用于转换外部形式的JSON text成一种可以由get和opt方法访问的内部形式,或者使用element方法和toString方法把值转换成为JSON text。如果name存在,则get会返回对应的值,否则会抛出异常JSONException。而opt方法则会在不存在所要检索的name时可以指定一个默认值而不是抛出异常,这样可以获取可选择值。
普通的get()和opt()方法会返回Object,因而可以对返回值进行强制类型转换。也可以使用类型化的get和opt方法进行类型审核和强转。
String myString = new JSONObject().put(“JSON”, “Hello, World!”).toString();
将会产生{“JSON”: “Hello, World”}
JSONArray是一个有序的值得序列。它的外部形式是包括在方括号[]内的字符串,由逗号分隔值。
[“aaa”, “bbb”, “ccc”]内部的形式是一个拥有get和opt方法的对象,这两个方法可以根据索引访问值,element方法可以用来添加和替换值。
这些值可以是任意类型
Boolean、 JSONObject、 JSONArray、 Number、 String、 或者JSONNull对象图示如下:
JSONArray的类型定义如下:
public final class JSONArray extends AbstractJSON implements JSON, List, Comparable { 因此在操作JSONArray对象时可以使用JSON接口、List接口以及Comparable接口提供的方法,可以把JSONArray看成一个List对象。
构造器可以把一个JSON text转换成为Java对象,toString方法转换成JSON text。
可以使用Maven快速导入该net.sf.json包,对应放入pom.xml依赖说明如下:
<dependency> <groupId>net.sf.json-lib</groupId><artifactId>json-lib</artifactId><version>2.4</version><classifier>jdk15</classifier></dependency>在pom.xml文件中添加上述的依赖,Import Changes即可。
注意:添加的依赖文件必须含有标记,不然maven无法从仓库中下载成功
JSONObject有两种常见的构造方法,一般常用的构造函数为JSONObject(),构造一个不含任何name/value的JSONObject对象
JSONObjectpublic JSONObject()Construct an empty JSONObject. JSONObjectpublic JSONObject(boolean isNull)Creates a JSONObject that is null. 由于JSONObject继承自Map接口,因此该类型自动的包含一些判断方法,简要介绍如下:
判空的含义是JSONObject对象中是否不包含任何name/value对映射。
public boolean isEmpty()Description copied from interface: JSONReturns true if this object has no elements or keys. Specified by:isEmpty in interface MapSpecified by:isEmpty in interface JSON<>4.2.2 判Null
判Null则对应构造函数的第二种形式,即该对象为null,而相应的在这类对象的基础上,如果添加了键值对,则会重新分配空间。
isNullObjectpublic boolean isNullObject()Returs if this object is a null JSONObject. public boolean containsKey(uObject key)Specified by:containsKey in interface Map该方法确保JSONObject中是否包含键的判断。
JSONObject对象也提供了has方法
public boolean has(String key)Determine if the JSONObject contains a specific key. Parameters:key - A key string. Returns:true if the key exists in the JSONObject.该接口继承自Map接口
public boolean containsValue(Object value)Specified by:containsValue in interface Map两个JSONObject对象相等表示两个JSONObject包含相同的键集合,同时每个键对应的值也相等。
public boolean equals(Object obj)Specified by:equals in interface MapOverrides:equals in class Object判断一个name对应的value类型是否为数组的方法声明如下:
public boolean isArray()Description copied from interface: JSONReturns true if this object is a JSONArray, false otherwise. Specified by:isArray in interface JSON在JSONObject中可以存放name/value的方法有如下几种:accumulate方法、element方法、put方法、putAll方法、在此简要介绍这几个方法的用处。
在JSONObject中由于name的类型为字符串类型,而值可以为JSONObject,JSONArray,Boolean、 JSONObject、 JSONArray、 Number、 String、 或者JSONNull对象。
在同一个name下,放置多个值,即组成JSONArray类型。
在下面的方法中,在一个key下累加一个值,如果已经有一个值为存储在key对应的对象中,该函数与element方法类似,此时会在key对应的位置存储一个JSONArray对象保存所有积累的值。如果已经有一个JSONArray对象,那么新值会追加到该JSONArray对象。作为对比,replace方法会替换之前的值。
public JSONObject accumulate(String key, boolean value)Accumulate values under a key. It is similar to the element method except that if there is already an object stored under the key then a JSONArray is stored under the key to hold all of the accumulated values. If there is already a JSONArray, then the new value is appended to it. In contrast, the replace method replaces the previous value. Parameters:key - A key string.value - An object to be accumulated under the key. Returns:this. Throws: JSONException - If the value is an invalid number or if the key is null.通过accumulate类方法可以把value累加到对应的name下而不会覆盖原有的value值而是形成一个JSONArray对象,不断追加新的Value。
类似的方法如下:
public JSONObject accumulate(String key, boolean value);public JSONObject accumulate(String key, double value);public JSONObject accumulate(String key, int value) ;public JSONObject accumulate(String key, long value) ;public JSONObject accumulate(String key, Object value);public JSONObject accumulate(String key, Object value, JsonConfig jsonConfig) ;public void accumulateAll(Map map);public void accumulateAll(Map map, JsonConfig jsonConfig) ;accumulate方法代码片段如下;
JSONArray array = new JSONArray();array.add("123");array.add(1);Map<String, Integer> val = new HashMap<>();val.put("1", 20);val.put("2", 30);System.out.println(array.toString());array.add(val);System.out.println(array.toString());JSONObject json = new JSONObject(true);System.out.println(json.isNullObject());//Can't accumulate on null object//json.accumulate("1", 1);//null object//json.put("1", 1);json = new JSONObject();json.accumulate("1", 1);json.accumulate("1", val);System.out.println(json.toString());json.putAll(val);System.out.println(json.toString());打印结果如下:["123",1]["123",1,{ "1":20,"2":30}]true{ "1":[1,{ "1":20,"2":30}]}{ "1":20,"2":30}阅读上述代码片段,可以看到几个注意点:
注意:如果使用构造器new
JSONObject(true);则构造出来的JSONObject对象无法accumulate和put。否则会抛出异常,由代码片段中的注释可以看出。
另外put方法会进行替换而不会追加到name对应的value集合中。 最后的json.putAll(val); 中有name
“1”,替换了之前”1”对应的集合。
在JSONObject中替换name对应的value时,可以使用put方法实现
JSONObject json = new JSONObject();SONArray jsonInner = new JSONArray();//java.lang.IndexOutOfBoundsException: Index: 5, Size: 0 //jsonInner.add(5, "1");for(int i=0; i<5; i++) { jsonInner.add(i);}json.put("1", jsonInner);System.out.println(json.toString());json.put("1", new int[]{ 1, 2, 6});System.out.println(json.toString());Map<String, String> vals = new HashMap<String, String>();vals.put("1", "sqh");vals.put("3", "lww");vals.put("2", "computer");json.putAll(vals);System.out.println(json.toString());向JSONObject对象中存储name/value对可以通过put存放。该接口继承自Map接口
当name已经存在于JSONObject中,实际作用是用新值替换旧值,与以下函数等价
json.replace(“1”, “sqh”);
还有一类增加的方法为elemnent方法
public JSONObject element(String key, double value)Put a key/double pair in the JSONObject. Parameters:key - A key string.value - A double which is the value. Returns:this. Throws: JSONException - If the key is null or if the number is invalid.该类方法与put方法类似,但由于element方法的返回值类型为JSONObject,因此可以使用链式存储的方式,非常方便。
element方法代码片段如下:
JSONObject json = new JSONObject();json.element("1", 1).element("2", 2);System.out.println(json.toString());json.element("1", 3).element("2", 4);System.out.println(json.toString());该代码片段运行结果如下:
{"1":1,"2":2}{"1":3,"2":4}从代码执行来看,第一次打印的值和第二次打印的值,分析得到实际执行取代了name ”1”和”2”的值。实际方法实现如下:
public JSONObject element(String key, int value) { this.verifyIsNull(); return this.element(key, (Object)(new Integer(value)));}上述为JDK代码对应的代码实现,存放时转化为(Object)类型。
public JSONObject element(String key, boolean value) ;public JSONObject element(String key, Collection value);public JSONObject element(String key, Collection value, JsonConfig jsonConfig);public JSONObject element(String key, double value) ;public JSONObject element(String key, int value) ;public JSONObject element(String key, long value);public JSONObject element(String key, Map value) ;public JSONObject element(String key, Map value, JsonConfig jsonConfig);public JSONObject element(String key, Object value) ;public JSONObject element(String key, Object value, JsonConfig jsonConfig) ;从JSONObject检索数据也提供了一些常用的方法,例如一些列的get方法,opt方法。介绍如下:
getpublic Object get(Object key)Specified by:get in interface Map________________________________________getpublic Object get(String key)Get the value object associated with a key. Parameters:key - A key string. Returns:The object associated with the key. Throws: JSONException - if this.isNull() returns true.上述的两个方法第一个方法继承自Map接口,因此key的类型为Object,返回值类型也为Object,由于返回值类型为根类型,因此需要强制转换为具体的类型。
getBooleanpublic boolean getBoolean(String key)Get the boolean value associated with a key. Parameters:key - A key string. Returns:The truth. Throws: JSONException - if the value is not a Boolean or the String "true" or "false".getBoolean方法如果key为null,或者值不是Boolean或者串”true”或”false”,会抛出JSONException异常。通过getXXX可以获取指定类型的Value而不需要强制转换,较为方便,
getBoolean方法实际实现如下:
public boolean getBoolean(String key) {this.verifyIsNull();Object o = this.get(key);if (o != null) { if (o.equals(Boolean.FALSE) || o instanceof String && ((String)o).equalsIgnoreCase("false")) { return false; } if (o.equals(Boolean.TRUE) || o instanceof String && ((String)o).equalsIgnoreCase("true")) { return true; } } throw new JSONException("JSONObject[" + JSONUtils.quote(key) + "] is not a Boolean.");}同类型的方法如下:
public boolean getBoolean(String key) ;public double getDouble(String key) {this.verifyIsNull(); Object o = this.get(key); if (o != null) { try { return o instanceof Number ? ((Number)o).doubleValue() : Double.parseDouble((String)o); } catch (Exception var4) { throw new JSONException("JSONObject[" + JSONUtils.quote(key) + "] is not a number."); } } else { throw new JSONException("JSONObject[" + JSONUtils.quote(key) + "] is not a number."); }}public int getInt(String key) ;public JSONArray getJSONArray(String key) ;public JSONObject getJSONObject(String key);public long getLong(String key) ;public String getString(String key) ;JSONObject同时提供了optXXX的方法获取name对应的value值。
public Object opt(String key) ;public boolean optBoolean(String key) ;public boolean optBoolean(String key, boolean defaultValue) ;public double optDouble(String key) ;public double optDouble(String key, double defaultValue);public int optInt(String key) ;public int optInt(String key, int defaultValue) ;public JSONArray optJSONArray(String key) ;public JSONObject optJSONObject(String key) { this.verifyIsNull(); Object o = this.opt(key); return o instanceof JSONObject ? (JSONObject)o : null;}public long optLong(String key);public long optLong(String key, long defaultValue) ;public String optString(String key) ;public String optString(String key, String defaultValue);optXXX的方法与getXXX最大的区别是,optXXX方法可以指定默认值。
optDoublepublic double optDouble(String key, double defaultValue)Get an optional double associated with a key, or the defaultValue if there is no such key or if its value is not a number. If the value is a string, an attempt will be made to evaluate it as a number. Parameters:key - A key string.defaultValue - The default. Returns:An object which is the value.在遍历JSONObject对象时,需要使用下述的方式。确保正确使用返回值,即迭代器或者Set集合,或者JSONArray
public Iterator keys()Get an enumeration of the keys of the JSONObject. Returns:An iterator of the keys.public Set keySet()Specified by:keySet in interface Mappublic JSONArray names()Produce a JSONArray containing the names of the elements of this JSONObject. Returns:A JSONArray containing the key strings, or null if the JSONObject is empty.public Set entrySet()Specified by:entrySet in interface Mappublic Collection values()Specified by:values in interface Map使用上述方法的代码片段如下:
JSONObject json = new JSONObject();json.element("1", new int[]{ 1, 2, 3}).element("2", (new JSONArray()).element(1).element(2));json.element("3", 5.6);json.element("4", "abc");for (Object str:json.keySet()) { String key = (String)str; System.out.println(json.get(key));}Set<Object> ss = json.entrySet();for (Object o:ss) { System.out.println(o);}Collection<Object> col = json.values();System.out.println(col);Iterator<Object> it = col.iterator();while(it.hasNext()) { //取出迭代器对应的值 System.out.println(it.next());}//从一个Map构造JSONObjectMap map = new HashMap();map.put( "name", "json" );map.put( "bool", Boolean.TRUE );map.put( "int", new Integer(1) );map.put( "arr", new String[]{ "a","b"} );map.put( "func", "function(i){ return this.arr[i]; }" );JSONObject jObject = JSONObject.fromObject( map );System.out.println( jObject );// prints ["name":"json","bool":true,"int":1,"arr":["a","b"],"func":func从Bean转换为JSONObject
class MyBean{ private String name = "json"; private int pojoId = 1; private char[] options = new char[]{ 'a','f'}; private String func1 = "function(i){ return this.options[i]; }"; private JSONFunction func2 = new JSONFunction(new String[]{ "i"},"return this.options[i];");}getset方法//从一个Java对象(Java Bean构造JSONObject) JSONObject jsonObject = JSONObject.fromObject( new MyBean() ); System.out.println( jsonObject );/* prints { "name":"json","pojoId":1,"options":["a","f"], "func1":function(i){ return this.options[i];}, "func2":function(i){ return this.options[i];}}*/JSONObject的演示代码如下:public class JSONObjectUse { public static void main(String[] args) { //创建JSONObject对象 JSONObject jsonObject = new JSONObject(); jsonObject.put("username","wln"); jsonObject.put("password","123"); System.out.println("1:" + jsonObject); //增加属性 jsonObject.element("sex","男"); System.out.println("2:" + jsonObject); //判断输出对象的类型 boolean isArray = jsonObject.isArray(); boolean isEmpty = jsonObject.isEmpty(); boolean isNullObject = jsonObject.isNullObject(); System.out.println("3:" + "是否是数组:" + isArray +" 是否是空:" + isEmpty + " 是否是空对象:" + isNullObject); //创建JSONArray JSONArray jsonArray = new JSONArray(); jsonArray.add(0,"aa"); jsonArray.add("BB"); jsonArray.add(1,"AB"); jsonArray.add("cc"); //将JSONArray 添加到JSONObject jsonObject.element("student",jsonArray); System.out.println("4:" + jsonObject); }}结果:
1:{ "username":"wln","password":"123"}2:{ "username":"wln","password":"123","sex":"男"}3:是否是数组:false 是否是空:false 是否是空对象:false4:{ "username":"wln","password":"123","sex":"男","student":["aa","AB","BB","cc"]}public class JSONArrayUse { public static void main(String[] args) { //创建JSONArray对象 JSONArray jsonArray = new JSONArray(); jsonArray.add(0,"aa"); jsonArray.add(1,"BB"); jsonArray.element("cc"); jsonArray.add("DD"); System.out.println("1:" + jsonArray); //根据下标获取数据 System.out.println("2:" + jsonArray.get(0)); //根据下标设置数据 jsonArray.set(0,"AAA"); System.out.println("3:" + jsonArray); //创建JSONObject JSONObject jsonObject = new JSONObject(); jsonObject.put("username", "lwc"); jsonObject.put("password", "123"); //把JSONObject放入到JSONArray中 jsonArray.add(jsonObject); System.out.println("4:" + jsonArray); //遍历 System.out.println("5:"); for(int i=0;i<jsonArray.size();i++){ System.out.print(jsonArray.get(i)+"\t"); } }}结果:
1:["aa","BB","cc","DD"]2:aa3:["AAA","BB","cc","DD"]4:["AAA","BB","cc","DD",{ "username":"lwc","password":"123"}]5:AAA BB cc DD { "username":"lwc","password":"123"}在使用JSONObject进行Java Web开发时,常用的便是json参数的解析和传送。在下述的代码片段中可以使用url进行访问:
url:localhost:8080/netjson?a=1&b=2同时使用postman工具指定url Body为
{ "name":"sqh", "pwd":"123", "phone":1234 }想要以一种非常方便的方式接受参数,则可以如下设置:
public JSONObject sfJsonTest(HttpServletRequest request, @RequestBody JSONObject content) { 通过指定@RequestBody类型为JSONObject,可以完成从JSON text到JSONObject的自动转换。
package com.example.demo;import net.sf.json.JSONObject;import org.springframework.web.bind.annotation.RequestBody;import org.springframework.web.bind.annotation.RequestMapping;import org.springframework.web.bind.annotation.ResponseBody;import org.springframework.web.bind.annotation.RestController;import javax.servlet.http.HttpServletRequest;@RestControllerpublic class NetSfJsonTest { @ResponseBody @RequestMapping("/netsfjson") public JSONObject sfJsonTest(HttpServletRequest request, @RequestBody JSONObject content) { System.out.println("?后的内容: "+request.getQueryString()); String name = (String)content.get("name"); Integer phone = (Integer)content.get("phone"); String pwd = (String)content.get("pwd"); JSONObject result = new JSONObject(); result.put("errCode", 200); result.put("errMsg", "success"); result.put("data", content); return result; }}由于在项目开发时必须以json的格式接受并且向前端以json的方式回传数据,因此比较熟悉某种json解析的方式非常有帮助。在C++开发时较为详细的了解了rapidJSON工具的使用,而Java开发时net.sf.json包的使用可以扮演同样的角色,熟练这个使用可以提升开发的效率。
文档位于
https://download.csdn.net/download/lk142500/10652591
www.json.org/json-zh.html
https://www.cnblogs.com/nananana/p/9263708.html