大概思路:
1.扫描出字符串
2.按顺序解析字符串
容易迷糊的地方
1.引用传递
2.解析逻辑
优点
1.能识别非标准json
2.一个类搞定
3.一次循环
缺点
1.非法string的值类型没做识别,懒得写了
package com.ics.sdk;
import java.math.BigInteger;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Set;
public class Json{
private Json parent;
private RegEx isInteger=new RegEx("^\\d+$");
private RegEx isDouble=new RegEx("^\\d*\\.\\d+$");
private RegEx isBoolean=new RegEx("^(true|false)$");
private boolean isArray=false;
private HashMap<String,Object> data=new HashMap<>();
private List<Object> array=new ArrayList<>();
public Json(){
ChangeToItem();
}
public Json(ResultSet resultSet) throws Issue{
ChangeToArray();
try{
ResultSetMetaData metaData=resultSet.getMetaData();
int keysLength=metaData.getColumnCount();
String[] keys=new String[keysLength];
for(int i=0;i<keysLength;i++){
keys[i]=metaData.getColumnLabel(i+1);
}
while(resultSet.next()){
Json item=new Json();
for(int i=0;i<keysLength;i++){
item.ItemSet(keys[i],resultSet.getString(keys[i]));
}
ArrayInsert(item);
}
}catch(SQLException e){
//e.printStackTrace();
throw new Issue("Json Init Issue",e);
}
}
public Json(String content) throws Issue{
int i=0;
int l=content.length();
StringBuffer v=new StringBuffer();
boolean wordIsKey=false;
Object wordTmp=null;
int readType=0;//识别当前值存在位置 0等待 1数组value 2数组end 3key 4key end 5value 6value end
char side=0;//当前值加载情况 0等待 1无引号 +引号
Json p=this;
Json j;
String key=null;
boolean isError=false;
boolean isEnd=false;
//扫描为字符串
while(i<l){
char w=content.charAt(i++);
switch(w){
case '[':
case ']':
case '{':
case '}':
case ':':
case ',':
if(side==0){
wordTmp=w;
wordIsKey=true;
}else if(side==1){
wordTmp=v.toString();
v=new StringBuffer();
wordIsKey=false;
side=0;
i--;
}else{
v.append(w);
}
break;
case '\'':
case '"':
if(side==0){
side=w;
}else if(side==1){
wordTmp=v.toString();
v=new StringBuffer();
wordIsKey=false;
side=w;
}else{
if(side==w&&content.charAt(i-2)!='\\'){
wordTmp=v.toString();
v=new StringBuffer();
wordIsKey=false;
side=0;
}else{
v.append(w);
}
}
break;
case ' ':
if(side==1){
wordTmp=v.toString();
v=new StringBuffer();
wordIsKey=false;
side=0;
}
if(side>1){
v.append(w);
}
break;
default:
if(side==0){
side=1;
}
v.append(w);
}
if(wordTmp!=null){//解析字符串
String word=wordTmp.toString();
wordTmp=null;
//Log.Info(word+"\n");
switch(readType){
case 0:
if(wordIsKey){
if(word.equals("[")){
ChangeToArray();
readType=1;
}else if(word.equals("{")){
ChangeToItem();
readType=3;
}else{
isError=true;
}
}else{
isError=true;
}
break;
case 1:
if(wordIsKey){
if(word.equals("[")){
j=new Json();
j.ChangeToArray();
j.parent=p;
p.ArrayInsert(j);
p=j;
readType=1;
}else if(word.equals("{")){
j=new Json();
j.parent=p;
p.ArrayInsert(j);
p=j;
readType=3;
}else{
isError=true;
}
}else{
SetValue(p,word);
readType=2;
}
break;
case 2:
if(wordIsKey){
if(word.equals(",")){
readType=1;
}else if(word.equals("]")){
p=p.parent;
if(p==null){
isEnd=true;
}else if(p.isArray){
readType=2;
}else{
readType=6;
}
}
}else{
isError=true;
}
break;
case 3:
if(wordIsKey){
isError=true;
}else{
key=word;
readType=4;
}
break;
case 4:
if(wordIsKey&&word.equals(":")){
readType=5;
}else{
isError=true;
}
break;
case 5:
if(wordIsKey){
if(word.equals("[")){
j=new Json();
j.ChangeToArray();
j.parent=p;
p.ItemSet(key,j);
p=j;
readType=1;
}else if(word.equals("{")){
j=new Json();
j.parent=p;
p.ItemSet(key,j);
p=j;
readType=3;
}else{
isError=true;
}
}else{
SetValue(p,key,word);
key=null;
readType=6;
}
break;
case 6:
if(wordIsKey){
if(word.equals(",")){
readType=3;
}else if(word.equals("}")){
p=p.parent;
if(p==null){
isEnd=true;
}else if(p.isArray){
readType=2;
}else{
readType=6;
}
}else{
isError=true;
}
}else{
isError=true;
}
break;
}
if(isEnd&&i<l||isError){
throw new Issue("index["+i+"]word["+word+"]\n"+content);
}
//Log.Info(word+"\n");
//Log.Info(isError+"\n");
}
}
//Log.Info(this);
}
public static void main(String[] args){
try{
//new Json(" {a:1,b:'2\\'3',c:{d:5,f:'{}[]:,\\'\"'}}");
//new Json(" [1,2,[4,5,6],[7,[8,[[9],10]]],[[[[11]]]]]");
//new Json(" [{a:1},9,{c:3}]");
new Json(" {a:1,b:[2,3],c:4]");//this is error
//new Json(" [{a:1},2,{c:3},'d',{f:[5,6],h:{i:7,j:[{g:8}]}}]");
}catch(Issue e){
Log.Info(e);
}
}
private Object GetValue(String value){
if(isInteger.Test(value)){
return new BigInteger(value);
}else if(isDouble.Test(value)){
return Double.parseDouble(value);
}else if(isBoolean.Test(value)){
return Boolean.parseBoolean(value);
}else{
return value;
}
}
private void SetValue(Json json,String key,String value){
json.ItemSet(key,GetValue(value));
}
private void SetValue(Json json,String value){
json.ArrayInsert(GetValue(value));
}
public void ChangeToItem(){
isArray=false;
}
public void ChangeToArray(){
isArray=true;
}
/*******************item*******************/
public boolean ItemExist(String key){
return data.containsKey(key);
}
public void ItemSet(String key,Object value){
data.put(key,value);
}
public Object ItemGet(String key){
return data.get(key);
}
public void ItemDelete(String key){
if(!isArray){
data.remove(key);
}
}
public String[] ItemKeys(){
Set<String> keySet=data.keySet();
String[] keys=new String[keySet.size()];
keySet.toArray(keys);
return keys;
}
/*******************array*******************/
public int ArrayLength(){
return array.size();
}
public int ArrayIndexOf(Object item){
return array.indexOf(item);
}
public boolean ArrayExist(Object item){
return ArrayIndexOf(item)>=0;
}
public Object ArrayGet(int index){
return array.get(index);
}
public Json ArrayGetJson(int index){
return (Json)ArrayGet(index);
}
public void ArrayInsert(Object item){
array.add(item);
}
public void ArrayInsert(Object item,int index){
array.add(index,item);
}
public void ArrayRemove(Object item){
array.remove(item);
}
public void ArrayRemove(int index){
array.remove(index);
}
/*******************table*******************/
public Object TableGet(int row,String key){
Json json=ArrayGetJson(row);
if(json==null){
return null;
}else{
return json.ItemGet(key);
}
}
public String TableGetString(int row,String key){
Object value=TableGet(row,key);
if(value==null){
return null;
}else{
return value.toString();
}
}
public int TableGetInteger(int row,String key) throws Issue{
Object value=TableGet(row,key);
try{
return Integer.parseInt(value.toString());
}catch(Exception e){
throw new Issue("row["+row+"]key["+key+"]value["+value+"]",e);
}
}
public double TableGetDouble(int row,String key) throws Issue{
Object value=TableGet(row,key);
try{
return Double.parseDouble(value.toString());
}catch(Exception e){
throw new Issue("row["+row+"]key["+key+"]value["+value+"]",e);
}
}
public String toString(){
String rs="";
if(isArray){
for(int i=0, l=array.size();i<l;i++){
rs+=","+array.get(i);
}
if(rs.length()>0){
rs=rs.substring(1);
}
return "["+rs+"]";
}else{
String[] keys=ItemKeys();
for(int i=0, l=keys.length;i<l;i++){
Object v=ItemGet(keys[i]);
if(v instanceof String){
v="\""+((String)v).replaceAll("\\\\","\\\\\\\\").replaceAll("\"","\\\\\"")+"\"";
}
rs+=",\""+keys[i]+"\":"+v;
}
if(rs.length()>0){
rs=rs.substring(1);
}
return "{"+rs+"}";
}
}
}