我有一个递归函数,它接受事件列表并按日期排序。它工作得很好,但今天我收到了关于Google Play开发者控制台的崩溃报告。抛出StackOverflowError。
所以,我的问题是,有人知道为什么会这样,以及该怎么做才能避免它?
我的排序功能:
public class SortEventDates {
public List<Event> sortDates(List<Event> eventList) {
int a, b, c, d, e, f, g, h, ix, j;
// Sorting
for (int i = 0; i < eventList.size() - 1; i++) {
a = Integer.valueOf(eventList.get(i).getDate().split("/")[2]); // <--Row 18
b = Integer.valueOf(eventList.get(i+1).getDate().split("/")[2]);
// Sorting years
if (a > b) {
Collections.swap(eventList, i, i+1);
sortDates(eventList);
} else if (a == b) {
c = Integer.valueOf(eventList.get(i).getDate().split("/")[0]);
d = Integer.valueOf(eventList.get(i+1).getDate().split("/")[0]);
// Sorting months
if (c > d) {
Collections.swap(eventList, i, i+1);
sortDates(eventList); // <-- Row 30
} else if (c == d) {
e = Integer.valueOf(eventList.get(i).getDate().split("/")[1]);
f = Integer.valueOf(eventList.get(i+1).getDate().split("/")[1]);
// Sorting days
if (e > f) {
Collections.swap(eventList, i, i+1);
sortDates(eventList); // <-- Row 37
} else if (e == f) {
g = Integer.valueOf(eventList.get(i).getTime().split(":")[0]);
h = Integer.valueOf(eventList.get(i+1).getTime().split(":")[0]);
// Sorting hours
if (g > h) {
Collections.swap(eventList, i, i+1);
sortDates(eventList);
} else if (g == h) {
ix = Integer.valueOf(eventList.get(i).getTime().split(":")[1]);
j = Integer.valueOf(eventList.get(i+1).getTime().split(":")[1]);
// Sorting minutes
if (ix > j) {
Collections.swap(eventList, i, i+1);
sortDates(eventList);
}
}
}
}
}
}
return eventList;
}
}
堆栈追踪:
java.lang.RuntimeException: An error occured while executing doInBackground()
at android.os.AsyncTask$3.done(AsyncTask.java:300)
at java.util.concurrent.FutureTask.finishCompletion(FutureTask.java:355)
at java.util.concurrent.FutureTask.setException(FutureTask.java:222)
at java.util.concurrent.FutureTask.run(FutureTask.java:242)
at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:231)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1112)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:587)
at java.lang.Thread.run(Thread.java:841)
Caused by: java.lang.StackOverflowError
at java.util.regex.Splitter.fastSplit(Splitter.java:46)
at java.lang.String.split(String.java:1842)
at java.lang.String.split(String.java:1824)
at app.android.arret.java.services.SortEventDates.sortDates(SortEventDates.java:18)
at app.android.arret.java.services.SortEventDates.sortDates(SortEventDates.java:37)
at app.android.arret.java.services.SortEventDates.sortDates(SortEventDates.java:37)
at app.android.arret.java.services.SortEventDates.sortDates(SortEventDates.java:37)
at app.android.arret.java.services.SortEventDates.sortDates(SortEventDates.java:30)
at app.android.arret.java.services.SortEventDates.sortDates(SortEventDates.java:37)
...
...
at app.android.arret.java.services.SortEventDates.sortDates(SortEventDates.java:30)
at app.android.arret.java.activity.DownloadJSON.doInBackground(DownloadJSON.java:119)
at app.android.arret.java.activity.DownloadJSON.doInBackground(DownloadJSON.java:24)
at android.os.AsyncTask$2.call(AsyncTask.java:288)
at java.util.concurrent.FutureTask.run(FutureTask.java:237)
答案 0 :(得分:3)
您知道Java Comparables,对吧?
基本用法:
public class Event implements Comparable<Event> {
private Date date;
public Event(Date date) {
this.date = date;
// Constructor
}
public Date getDate() {
return date;
}
@Override
public int compareTo(Event e) {
if (getDate() == null || e.getDate() == null) {
return 0;
}
return getDate().compareTo(e.getDate());
}
}
然后调用此选项对列表进行排序:
Collections.sort(eventList);
或者,如果您不想修改模型,可以执行以下操作:
Collections.sort(eventList, new Comparator<Event>() {
public int compare(Event e1, Event e2) {
if (e1.getDate() == null || e2.getDate() == null) {
return 0;
}
return e1.getDate().compareTo(e2.getDate());
}
});
答案 1 :(得分:1)
你永远不会从你的重复呼叫中返回。根据输入集上的程序的堆栈跟踪,一旦你递归调用你的函数,它永远不会返回
var items = [{
id: 1,
name: "one"
}, {
id: 2,
name: "two"
}];
function MyCtrl($scope) {
$scope.items = items;
$scope.send = function() {
//get items' id
$scope.items.forEach(function(item){
alert(item.id);
}, this);
}
}
此函数将被无限调用,并将导致堆栈溢出。 您需要通过这些调用提供重新调度条件。
答案 2 :(得分:0)
你也可以使用Java 8流进行排序:
Comparator<Event> sortByDate = new Comparator<Event>() {
public int compare(Event left, Event right) {
if (left.getDate().isBefore(right.getDate())) {
return -1;
} else {
return 1;
}
}
};
Collections.sort(events, sortByDate);