Java 如何修复使用gson.fromJson时的NumberFormatException

Java 如何修复使用gson.fromJson时的NumberFormatException,java,android,json,gson,Java,Android,Json,Gson,我在共享首选项中保存了一个自定义对象(书籍)的arraylist,现在我已经更新了应用程序(添加了一个名为Progress的新属性,它是一个int),似乎gson正在尝试将一个long放入这个int变量中 这种情况只发生在一些特定的用户身上,他们通过商店下载应用程序,而我无法复制它。我昨天在这里发布了一些类似的东西,但是没有足够的信息,我意识到我发布得太早了 注意:myrr.auto1.myreadingrecord1.sharedFunctions.loadArrayList(sharedFu

我在共享首选项中保存了一个自定义对象(书籍)的arraylist,现在我已经更新了应用程序(添加了一个名为Progress的新属性,它是一个int),似乎gson正在尝试将一个long放入这个int变量中

这种情况只发生在一些特定的用户身上,他们通过商店下载应用程序,而我无法复制它。我昨天在这里发布了一些类似的东西,但是没有足够的信息,我意识到我发布得太早了

注意:myrr.auto1.myreadingrecord1.sharedFunctions.loadArrayList(sharedFunctions.java:40)是 bookList=gson.fromJson(json,类型); 线

这是Book类的属性,setter和getter非常正常,所以我没有包括它们

public class Book implements Serializable{
private String author;
private String title;
private String pages;
private String imageURL;
private String description;
private String categories;
private String moreInfoLink;
private String language;
private int progress = 0;
private long startTime = 0L;
private long endTime = 0L;

public Book (String author, String title, String pages, String description, String imageURL, String categories, String moreInfoLink, String language) {
    this.author = author;
    this.title = title;
    this.pages = pages;
    this.description = description;
    this.imageURL = imageURL;
    this.categories = categories;
    this.moreInfoLink = moreInfoLink;
    this.language = language;
}
因此,对于某些用户,fromJson会尝试将starttime或endtime值放入new progress属性中。我怎样才能防止这种情况

它应该只是创建一个新的书的ArrayList,但实际上它只是崩溃了

添加:

public void setEndTime(long endTime) {
    this.endTime = endTime;
}

public void setStartTime(long startTime) {
    this.startTime = startTime;}

theCRBook.setStartTime(Calendar.getInstance().getTimeInMillis());

异常状态
1538513480946
太大,无法放入
int
,这是正确的。它是2018年2月10日上午8:51(UTC)的时间戳,应存储为
long


可能您有一个较旧版本的
Book
类,其中
startTime
endTime
声明为
int
,而不是
long
(或者可能只是setter参数是
int
)。

异常状态
1538513480946
太大,无法放入
int
,这是正确的。它是2018年2月10日上午8:51(UTC)的时间戳,应存储为
long


可能您有一个较旧版本的
Book
类,其中
startTime
endTime
声明为
int
,而不是
long
(或者可能只是setter参数是
int
)。

如错误所示,您在
build.gradle
中启用了
minifyEnabled
,以混淆代码。在这种情况下,您需要执行
@SerializedName(“endTime”)
@SerializedName(“startTime”)
。。。对于模型中的每个变量,等等,因为该变量的名称将在发布版本中更改

public class Book implements Serializable {

    @SerializedName("author")
    private String author;

    @SerializedName("title")
    private String title;

    @SerializedName("pages")
    private String pages;

    @SerializedName("imageURL")
    private String imageURL;

    @SerializedName("description")
    private String description;

    @SerializedName("categories")
    private String categories;

    @SerializedName("moreInfoLink")
    private String moreInfoLink;

    @SerializedName("language")
    private String language;

    @SerializedName("progress")
    private int progress = 0;

    @SerializedName("startTime")
    private long startTime = 0L;

    @SerializedName("endTime")
    private long endTime = 0L;

    public Book (String author, String title, String pages, String description, String imageURL, String categories, String moreInfoLink, String language) {
        this.author = author;
        this.title = title;
        this.pages = pages;
        this.description = description;
        this.imageURL = imageURL;
        this.categories = categories;
        this.moreInfoLink = moreInfoLink;
        this.language = language;
    }
}

如错误所示,您在
build.gradle
中启用了
minifyEnabled
,以混淆代码。在这种情况下,您需要执行
@SerializedName(“endTime”)
@SerializedName(“startTime”)
。。。对于模型中的每个变量,等等,因为该变量的名称将在发布版本中更改

public class Book implements Serializable {

    @SerializedName("author")
    private String author;

    @SerializedName("title")
    private String title;

    @SerializedName("pages")
    private String pages;

    @SerializedName("imageURL")
    private String imageURL;

    @SerializedName("description")
    private String description;

    @SerializedName("categories")
    private String categories;

    @SerializedName("moreInfoLink")
    private String moreInfoLink;

    @SerializedName("language")
    private String language;

    @SerializedName("progress")
    private int progress = 0;

    @SerializedName("startTime")
    private long startTime = 0L;

    @SerializedName("endTime")
    private long endTime = 0L;

    public Book (String author, String title, String pages, String description, String imageURL, String categories, String moreInfoLink, String language) {
        this.author = author;
        this.title = title;
        this.pages = pages;
        this.description = description;
        this.imageURL = imageURL;
        this.categories = categories;
        this.moreInfoLink = moreInfoLink;
        this.language = language;
    }
}

您还可以将该类用于book类:

public class Book {
    @SerializedName("author")
    @Expose
    private String author;
    @SerializedName("categories")
    @Expose
    private String categories;
    @SerializedName("description")
    @Expose
    private String description;
    @SerializedName("endTime")
    @Expose
    private long endTime;
    @SerializedName("imageURL")
    @Expose
    private String imageURL;
    @SerializedName("language")
    @Expose
    private String language;
    @SerializedName("moreInfoLink")
    @Expose
    private String moreInfoLink;
    @SerializedName("pages")
    @Expose
    private String pages;
    @SerializedName("startTime")
    @Expose
    private long startTime;
    @SerializedName("title")
    @Expose
    private String title;

    public String getAuthor() {
        return author;
    }

    public void setAuthor(String author) {
        this.author = author;
    }

    public String getCategories() {
        return categories;
    }

    public void setCategories(String categories) {
        this.categories = categories;
    }

    public String getDescription() {
        return description;
    }

    public void setDescription(String description) {
        this.description = description;
    }

    public long getEndTime() {
        return endTime;
    }

    public void setEndTime(long endTime) {
        this.endTime = endTime;
    }

    public String getImageURL() {
        return imageURL;
    }

    public void setImageURL(String imageURL) {
        this.imageURL = imageURL;
    }

    public String getLanguage() {
        return language;
    }

    public void setLanguage(String language) {
        this.language = language;
    }

    public String getMoreInfoLink() {
        return moreInfoLink;
    }

    public void setMoreInfoLink(String moreInfoLink) {
        this.moreInfoLink = moreInfoLink;
    }

    public String getPages() {
        return pages;
    }

    public void setPages(String pages) {
        this.pages = pages;
    }

    public long getStartTime() {
        return startTime;
    }

    public void setStartTime(long startTime) {
        this.startTime = startTime;
    }

    public String getTitle() {
        return title;
    }

    public void setTitle(String title) {
        this.title = title;
    }
}
只需在book类中导入gson: 导入com.google.gson.annotations.Expose; 导入com.google.gson.annotations.SerializedName

之后,您可以很容易地从书本数组中获取一些开始/结束时间,并将其转换为日期,如下所示:

ArrayList<Book> books = loadArrayList(this);
Date date = new Date(books.get(0).getStartTime());
Log.i(TAG, "Date: " + date.toString());
ArrayList books=loadArrayList(此);
日期日期=新日期(books.get(0.getStartTime());
Log.i(标记“Date:+Date.toString());
您将从json字符串中获取日期: 日期:2019年1月3日星期四17:13:47东部标准时间


希望这可以帮助您:)

您也可以将此类用于图书类:

public class Book {
    @SerializedName("author")
    @Expose
    private String author;
    @SerializedName("categories")
    @Expose
    private String categories;
    @SerializedName("description")
    @Expose
    private String description;
    @SerializedName("endTime")
    @Expose
    private long endTime;
    @SerializedName("imageURL")
    @Expose
    private String imageURL;
    @SerializedName("language")
    @Expose
    private String language;
    @SerializedName("moreInfoLink")
    @Expose
    private String moreInfoLink;
    @SerializedName("pages")
    @Expose
    private String pages;
    @SerializedName("startTime")
    @Expose
    private long startTime;
    @SerializedName("title")
    @Expose
    private String title;

    public String getAuthor() {
        return author;
    }

    public void setAuthor(String author) {
        this.author = author;
    }

    public String getCategories() {
        return categories;
    }

    public void setCategories(String categories) {
        this.categories = categories;
    }

    public String getDescription() {
        return description;
    }

    public void setDescription(String description) {
        this.description = description;
    }

    public long getEndTime() {
        return endTime;
    }

    public void setEndTime(long endTime) {
        this.endTime = endTime;
    }

    public String getImageURL() {
        return imageURL;
    }

    public void setImageURL(String imageURL) {
        this.imageURL = imageURL;
    }

    public String getLanguage() {
        return language;
    }

    public void setLanguage(String language) {
        this.language = language;
    }

    public String getMoreInfoLink() {
        return moreInfoLink;
    }

    public void setMoreInfoLink(String moreInfoLink) {
        this.moreInfoLink = moreInfoLink;
    }

    public String getPages() {
        return pages;
    }

    public void setPages(String pages) {
        this.pages = pages;
    }

    public long getStartTime() {
        return startTime;
    }

    public void setStartTime(long startTime) {
        this.startTime = startTime;
    }

    public String getTitle() {
        return title;
    }

    public void setTitle(String title) {
        this.title = title;
    }
}
只需在book类中导入gson: 导入com.google.gson.annotations.Expose; 导入com.google.gson.annotations.SerializedName

之后,您可以很容易地从书本数组中获取一些开始/结束时间,并将其转换为日期,如下所示:

ArrayList<Book> books = loadArrayList(this);
Date date = new Date(books.get(0).getStartTime());
Log.i(TAG, "Date: " + date.toString());
ArrayList books=loadArrayList(此);
日期日期=新日期(books.get(0.getStartTime());
Log.i(标记“Date:+Date.toString());
您将从json字符串中获取日期: 日期:2019年1月3日星期四17:13:47东部标准时间



希望这能帮助您:)

我已经检查过了,开始时间和结束时间从一开始就很长。我正在添加更多与这两个字段相关的代码。我已经检查过了,startTime和endTime从一开始就很长。我正在添加更多与这两个字段相关的代码。您的代码对我来说很好。我要做的唯一编辑就是添加方括号,因为您正在将这个json解析为一个列表。是的,它对我也适用,但一些用户崩溃,唯一的方法是完全删除应用程序数据(因此共享首选项被删除)。我甚至尝试过在旧的分支上添加书籍,并对新分支进行更新,这对我很有效。@lasagnakid77查看我的更新答案,我认为这会有所帮助。你的代码对我来说很好。我要做的唯一编辑就是添加方括号,因为您正在将这个json解析为一个列表。是的,它对我也适用,但一些用户崩溃,唯一的方法是完全删除应用程序数据(因此共享首选项被删除)。我甚至尝试过在旧的分支上添加书籍,并对新分支进行更新,这对我很有效。@lasagnakid77查看我的更新答案,我认为这会有所帮助。实际上,我一直都启用了该功能,就在最近,我更改了proguard设置以显示行号。我应该在哪里添加这个?在我得到字符串/longs?@lasagnakid77的书类中,我更新了答案并添加了类以及它应该是什么样子。@lasagnakid77因为在启用缩小后字符串不会更改,
@SerializedName(“”
)将使用java变量匹配共享首选项的名称,非常感谢。我没有办法测试它是否修复了它,但如果一天左右没有崩溃,我会接受答案。你知道为什么这只发生在一些人身上吗?不同的手机缩小的方式不同吗?不幸的是,我不知道。实际上我一直都启用了这个功能,最近我更改了proguard设置以显示行号。我应该在哪里添加这个?在我获取字符串/longs?@lasagnakid77的图书类中,我更新了答案,并添加了类及其应该如何添加。@lasagnakid77因为在启用缩小后字符串不会更改,
@SerializedName(“”
)将匹配名称