我能够读取包含消息列表及其相应作者的JSON文件。单个消息的结构如下:
JSON
{
"created_at": "Thu Apr 30 10:47:49 +0000 2015",
"id": 593728455901990900,
"user": {
"id": 12,
"name": "GiGi",
"user_date": "Thu May 17 10:47:49 +0000 2010"
}
}
作者和消息类(POJO)包含我们要解析的字段以及显示字符串中字段的函数 toString()。
作者
public class Author {
@SerializedName("id")
private static long id;
@SerializedName("created_at")
private static String user_date;
private static String name;
public String toString() {
return name + "\n" + id + "\n" + user_date;
}
....Getters & Setters....
}
消息
public class Message {
@SerializedName("user")
Author author;
@SerializedName("created_at")
String date;
long id;
public String toString() {
return id + "\n" + date;
}
}
作者是Message类的成员类,我需要显示按用户分组的消息,但我似乎找不到一种优雅的方式。
更新
解决方案是创建一个Map,其中一个作者的属性为KEY(在此代码示例中为作者的id),相应的消息列表为VALUE。
Map<Long, List<Message>> map = new HashMap<Long, List<Message>>();
for (Message msg : listOfMessages) {
long key = msg.getAuthor().getId();
if (map.get(key) == null) {
map.put(key, new ArrayList<Message>());
}
map.get(key).add(msg);
}
可以从此解决方案中获得的问题:
解
在Author类中添加 equals 和 hashCode 方法后,我们可以将Author实例映射为Keys。
@Override
public int hashCode() {
int hash = 7;
hash = 23 * hash + (int) (this.id ^ (this.id >>> 32));
return hash;
}
@Override
public boolean equals(Object obj) {
if (obj == null) {
return false;
}
if (getClass() != obj.getClass()) {
return false;
}
final Author author = (Author) obj;
if (this.id != author.id) {
return false;
}
return true;
}
在主类中,我们可以遍历消息列表并正确填充地图:
Map<Author, List<Message>> map = new HashMap<Author, List<Message>>();
for (Message message : listOfMessages) {
List<Message> userMessages = map.get(message.getAuthor());
if (userMessages == null) {
userMessages = new ArrayList<Message>();
map.put(message.getAuthor(), userMessages);
}
userMessages.add(message);
}
for (Entry<Author, List<Message>> entry : map.entrySet()) {
System.out.println(entry.getKey().getId());
for (Message message : entry.getValue()) {
System.out.println("\t" + message.getDate());
}
}
输出
3037057186
Thu Apr 30 10:47:52 +0000 2015
1598532858
Thu Apr 30 10:47:51 +0000 2015
67267979
Thu Apr 30 11:47:49 +0000 2015
Thu Apr 30 10:47:49 +0000 2015
Thu Apr 30 10:47:49 +0000 2015
Thu Apr 30 10:47:49 +0000 2015
答案 0 :(得分:2)
考虑这个json文件example.json
[
{
"date":"Thu Apr 30 10:47:49 +0000 2015",
"id":593728455901990912,
"author":{
"id":12,
"name":"GiGi",
"user_date":"Thu May 17 10:47:49 +0000 2010"
}
},
{
"date":"Thu Apr 30 10:47:49 +0000 2013",
"id":593728455901990977,
"author":{
"id":12,
"name":"GiGi",
"user_date":"Thu May 17 10:47:49 +0000 2010"
}
},
{
"date":"Thu Apr 30 10:47:49 +0000 2015",
"id":593728422901330999,
"author":{
"id":13,
"name":"HiHi",
"user_date":"Thu May 17 10:47:49 +0000 2015"
}
}
]
作者类
class Author {
private long id;
private String name;
private String user_date;
public String toString() {
return name + " " + id + " " + user_date;
}
//getters, setters,...
}
消息类
class Message {
String date;
long id;
Author author;
public String toString() {
return id + " " + date;
}
//getters, setters,...
}
使用Gson API解析json
Gson gson = new Gson();
List<Message> list = gson.fromJson(new BufferedReader(new FileReader(
"example.json")), new TypeToken<List<Message>>() {
}.getType());
显示按用户ID分组的消息
Map<Long, List<Message>> groupedMap = list.stream().collect(
Collectors.groupingBy(m-> m.getAuthor().getId()));
groupedMap.forEach((k, v) -> System.out.println(k + " => " + v));
输出:
12 => [593728455901990912 Thu Apr 30 10:47:49 +0000 2015, 593728455901990977 Thu Apr 30 10:47:49 +0000 2013]
13 => [593728422901330999 Thu Apr 30 10:47:49 +0000 2015]
答案 1 :(得分:1)
首先,发布的JSON无效。您需要添加封闭括号并删除用户部分中的最后一个逗号。所以改变
"created_at":"Thu Apr 30 10:47:49 +0000 2015",
"id":593728455901990912,
"user":{
"id":12,
"name":"GiGi",
"user_date":"Thu May 17 10:47:49 +0000 2010",
}
到
{
"created_at": "Thu Apr 30 10:47:49 +0000 2015",
"id": 593728455901990900,
"user": {
"id": 12,
"name": "GiGi",
"user_date": "Thu May 17 10:47:49 +0000 2010"
}
}
您还需要将getter和setter添加到Author
类,并使属性为非静态,以便解析器设置属性,在本例中为GSON。
然后,只需按用户对消息进行分组:
Map<Long, List<Message>> userGroup = new HashMap<>();
for (Message message : messages) {
List<Message> userMessages = userGroup.get(message.author.getId());
if (userMessages == null) {
userMessages = new ArrayList<>();
userGroup.put(message.author.getId(), userMessages);
}
userMessages.add(message);
}
for (Entry<Long, List<Message>> entry : userGroup.entrySet()) {
for (Message message : entry.getValue()) {
System.out.println(entry.getKey() + " : " + message.date);
}
}
<强>更新强>
您可以通过Author
和equals
类添加hashCode
和Author
方法,按@Override
public int hashCode() {
int hash = 7;
hash = 23 * hash + (int) (this.id ^ (this.id >>> 32));
return hash;
}
@Override
public boolean equals(Object obj) {
if (obj == null) {
return false;
}
if (getClass() != obj.getClass()) {
return false;
}
final Author other = (Author) obj;
if (this.id != other.id) {
return false;
}
return true;
}
键入。像这样:
Author
这样您就可以按Long
而不是Map<Author, List<Message>> userGroup = new HashMap<>();
for (Message message : messages) {
List<Message> userMessages = userGroup.get(message.author);
if (userMessages == null) {
userMessages = new ArrayList<>();
userGroup.put(message.author, userMessages);
}
userMessages.add(message);
}
for (Entry<Author, List<Message>> entry : userGroup.entrySet()) {
System.out.println(entry.getKey().getId());
for (Message message : entry.getValue()) {
System.out.println("\t" + message.date);
}
}
signature_tuple = signature.split(",")