欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  移动技术

android解析JSON数据

程序员文章站 2024-02-28 09:03:46
jsonobject的使用  一、 json对象的使用: string content = "{'username': 'linux', 'passw...

jsonobject的使用

 一、 json对象的使用:

string content = "{'username': 'linux', 'password': '123456'}";
jsonobject jsonobject = new jsonobject(content);
string username = jsonobject.getstring("username");
string password = jsonobject.getstring("password");

二、 json数组的使用:

string jsoncontent = "[{'user': '刘力', 'age': 21, 'femal': true}, "
            + "{'user': 'chen', 'age': 20, 'femal': false}]";
jsonarray jsonarray = new jsonarray(jsoncontent);
for (int i = 0; i < jsonarray.length(); i++) {
   jsonobject object = jsonarray.getjsonobject(i);
   system.out.print(object.getstring("user") + " ");
   system.out.print(object.getint("age") + " ");
   system.out.print(object.getboolean("femal") + " ");
   system.out.println();
}

三、 json数组与json对象混合使用

string jsonstring = "[{'user': 'tomhu', 'age': 21, " + "'info': {'adress': 'hubai', 'sex': 'femal'}}, "
          + "{'user': 'chen', 'age': 20, " + "'info': {'adress': 'hunan', 'sex': 'male'}}]";
jsonarray jsonarrays = new jsonarray(jsonstring);
for (int i = 0; i < jsonarrays.length(); i++) {
  jsonobject objects = jsonarrays.getjsonobject(i);
  system.out.print(objects.getstring("user") + " ");
  system.out.print(objects.getint("age") + " ");
  system.out.print(objects.getjsonobject("info").getstring("adress") + " ");
  system.out.print(objects.getjsonobject("info").getstring("sex") + " ");
  system.out.println();
}

四、 json数组中存储对象

person person = new person();
person.setusername("linux" );
person.setpassword("123456" );
jsonarray jsonarray = new jsonarray();
jsonarray.put(0, person );
jsonarray.put(1, "i love you" );

// string username = jsonarray.getjsonobject(0).getstring("username"); 错误的写法
person user = (person) jsonarray.get(0);
system.out.println("username: " + user.getusername());

jsonobject的原理

jsonobject的存储与取出

一、 jsonobject里面维护了一个linkedhashmap,当生成一个无参数的jsonobject,实质是初始化了一个map:

private final linkedhashmap<string, object> namevaluepairs;
public jsonobject() {
  namevaluepairs = new linkedhashmap<string, object>();
}

 二、 当jsonobject增加数据,实质上把数据的键值对方法存放在上述的map中:

public jsonobject put(string name, boolean value) throws jsonexception {
  namevaluepairs.put(checkname(name), value);
  return this;
}

三、 从jsonobject中取出数据,很容易想到的就是从map取出了:

public string getstring(string name) throws jsonexception {
  object object = get(name); // get()方法就是执行object result = namevaluepairs.get(name);
  string result = json.tostring(object);
  if (result == null) {
    throw json.typemismatch(name, object, "string");
  }
  return result;
}

jsonobject的解析过程

一、 jsonobject还有一个带参数的构造函数:常用的是传递一个string类型的参数

public jsonobject(string json) throws jsonexception {
  this(new jsontokener(json));
}

二、 跟进去,发现主要执行的是jsontokener的nextvalue()方法,在这个方法中主要是对数据进行解析;

public object nextvalue() throws jsonexception {
  int c = nextcleaninternal();
  switch (c) {
    case -1:
      throw syntaxerror("end of input");

    case '{':
      return readobject();

    case '[':
      return readarray();

    case '\'':
    case '"':
      return nextstring((char) c);

    default:
      pos--;
      return readliteral();
  }
}

在nextcleaninternal方法中,它会从头到尾的逐个字符的解析,对于一些字符做一些处理。例如空格,换行,转义符等!
当解析到[表示开始一个对象的读取,当解析到{表示一个数组的读取

三、 在readobject方法中,仍然是调用nextcleaninternal()方法,逐个得到解析的字符,下到解析到}.下面贴出重要代码

int first = nextcleaninternal(); // 得到解析的字符
if (first == '}') {
  return result;
} else if (first != -1) {
  pos--;
}
.......
while (true) {
  object name = nextvalue(); // 解析得到键
  
  int separator = nextcleaninternal();
  if (separator != ':' && separator != '=') {
    throw syntaxerror("expected ':' after " + name);
  }
  if (pos < in.length() && in.charat(pos) == '>') {
    pos++;
  }

  result.put((string) name, nextvalue()); // 将解析得到的键值对,存放在map当中

  switch (nextcleaninternal()) {
    case '}':
      return result;
    case ';':
    case ',':
      continue;
    default:
      throw syntaxerror("unterminated object");
  }
}

四、 nextvalue方法比较关键,它流转解析的大部分工作!在nextvalue中有一个readliteral方法,针对一些类型做处理,得到解析之后的结果:

private object readliteral() throws jsonexception {
  string literal = nexttointernal("{}[]/\\:,=;# \t\f");

  if (literal.length() == 0) {
    throw syntaxerror("expected literal value");
  } else if ("null".equalsignorecase(literal)) {
    return jsonobject.null;
  } else if ("true".equalsignorecase(literal)) {
    return boolean.true;
  } else if ("false".equalsignorecase(literal)) {
    return boolean.false;
  }

  /* try to parse as an integral type... */
  if (literal.indexof('.') == -1) {
    int base = 10;
    string number = literal;
    if (number.startswith("0x") || number.startswith("0x")) {
      number = number.substring(2);
      base = 16;
    } else if (number.startswith("0") && number.length() > 1) {
      number = number.substring(1);
      base = 8;
    }
    try {
      long longvalue = long.parselong(number, base);
      if (longvalue <= integer.max_value && longvalue >= integer.min_value) {
        return (int) longvalue;
      } else {
        return longvalue;
      }
    } catch (numberformatexception e) {
      /*
       * this only happens for integral numbers greater than
       * long.max_value, numbers in exponential form (5e-10) and
       * unquoted strings. fall through to try floating point.
       */
    }
  }

  /* ...next try to parse as a floating point... */
  try {
    return double.valueof(literal);
  } catch (numberformatexception ignored) {
  }

  /* ... finally give up. we have an unquoted string */
  return new string(literal); // a new string avoids leaking memory
}

五、至于jsonarray的解析与jsonobject的解析过程是一样的,它里面维护的是一个list:

private final list<object> values;
public jsonarray(jsontokener readfrom) throws jsonexception {
  object object = readfrom.nextvalue();
  if (object instanceof jsonarray) {
    values = ((jsonarray) object).values;
  } else {
    throw json.typemismatch(object, "jsonarray");
  }
}

gson的使用

一、我们在测试当中先加入一个person类,方便测试:

package com.tomhu.test;

public class person {
  private string name;
  private int age;

  public string getname() {
    return name;
  }
  public void setname(string name) {
    this.name = name;
  }
  public int getage() {
    return age;
  }
  public void setage(int age) {
    this.age = age;
  }
}

二、 gson把对象转换成json格式

gson gson = new gson();
person person = new person();
person.setname("linux");
person.setage(23);
string str = gson.tojson(person);
system.out.println(str);

打印结果:  {"name":"linux","age":23}

三、 gson把json格式解析成对象

string jsondata = "{'name':'刘力','age':19}";
person person = gson.fromjson(jsondata, person.class);
system.out.println(person.getname() + ", " + person.getage());

打印结果: 刘力, 19

四、 gson把list对象解析成json格式:

gson gson = new gson();
list<person> persons = new arraylist<person>();
for (int i = 0; i < 2; i++) {
   person p = new person();
   p.setname("name" + i);
   p.setage(i * 5);
   persons.add(p);
}
string str = gson.tojson(persons);
system.out.println(str);

打印结果: [{"name":"name0","age":0},{"name":"name1","age":5}]

五、 gson把json格式解析成list对象:

gson gson = new gson();
string str = "[{'name':'linux','age':10},{'name':'huhx','age':22}]";
list<person> ps = gson.fromjson(str, new typetoken<list<person>>(){}.gettype());
for (int i = 0; i < ps.size(); i++) {
  person person = ps.get(i);
  system.out.print("name: " + person.getname() + " age: " + person.getage());
}

打印结果:name: linux age: 10 name: huhx age: 22