Возможный дубликат:
RuntimeException: невозможно создать обработчик внутри потока, который не вызвал Looper.prepare()
У меня проблема с использованием механизма Java Serialization в Android. Он хорошо работает при вызове из потока пользовательского интерфейса, но когда я пытаюсь использовать его из некоторого фонового потока, я получаю:
java.lang.RuntimeException: Can't create handler inside thread that has not called Looper.prepare()
Из-за природы проекта я не могу десериализовать все в потоке пользовательского интерфейса (также должно быть возможно сделать это в фоновом режиме, поэтому пользовательский интерфейс не перестанет отвечать).
КСТАТИ. То же самое происходит, когда я пытаюсь десериализовать что-то в фоновом режиме с помощью SimpleXML.
Итак, теперь мы делаем десериализацию (как XML, так и сериализацию Java) из потока пользовательского интерфейса, который не может использоваться повсеместно.
Может ли кто-нибудь пролить свет на эту проблему?
РЕДАКТИРОВАТЬ:
Я использую следующий код для десериализации объекта, он хорошо работает при вызове из потока пользовательского интерфейса.
public Object getObject(String key) throws InvalidClassException {
Object result;
try {
FileInputStream fileIn = context.openFileInput(getPath(key));
ObjectInputStream in = new ObjectInputStream(fileIn);
result = in.readObject();
in.close();
fileIn.close();
} catch (InvalidClassException e) {
throw new InvalidClassException(e.getMessage());
} catch (IOException e) {
throw new RuntimeException(e);
} catch (ClassNotFoundException e) {
throw new RuntimeException(e);
}
return result;
}
EDIT 2
Как упоминалось в комментарии EJP ниже, я десериализую объект Activity. Поэтому я изменяю свой запрос: Как десериализовать объект Activity в фоновом потоке? Не десериализация этого объекта - это вариант, который я бы предпочел избежать из-за проблем с производительностью (XML десериализуется примерно за 4 с, а двоичная десериализация - менее 0,5 с). Я знаю, что можно было бы перепроектировать наше приложение, но из-за ограничений проекта и его чрезвычайной и ненужной сложности это не вариант. Все большие изменения чрезвычайно болезненны.
Поэтому, когда вопрос немного ясен - есть ли у кого-нибудь идеи?
Спасибо за любые предложения.
вы не можете выполнять операции ui в любом другом потоке, все операции ui должны быть на mainthread
вы можете использовать это
runOnUiThread(new Runnable() {
@Override
public void run() {
code here
}
});
Попробуйте вызвать Loooper.Prepare();
перед вашим кодом и Looper.Loop();
после, работа для меня.
Что-то вроде:
Looper.Prepare();
//your code
Looper.Loop();