Форум программистов, компьютерный форум CyberForum.ru
Наши страницы

Программирование Android

Войти
Регистрация
Восстановить пароль
 
 
Рейтинг: Рейтинг темы: голосов - 16, средняя оценка - 4.94
MonStar
19 / 19 / 3
Регистрация: 10.04.2011
Сообщений: 225
#1

Оптимизация приложения. Слишком часто вызывается GC - Программирование Android

16.07.2013, 15:30. Просмотров 2134. Ответов 28
Метки нет (Все метки)

Требуются некоторые разъяснения по работе GC и некоторая помощь в оптимизации.

Есть два проблемных места, в обоих очень часто создаются модели JSON.

Дело в том что постоянно через WebSocket идет непрерывный поток примерно 10Кб\с. Для каждого сообщения создается JSON, парсится, обрабатывается и когда приходит следующее сообщение старый JSON теряет ссылку и подбирается GC (мне кажется что всё происходит именно так).

В результате на момент работы GC приложение приостанавливается и появляются задержки.
Меня интересует, правда ли что GC_CONCURRENT полностью блокирует приложение на время своей работы (хотя он должен работать синхронно с приложением). По логам видно, что утечек памяти нет, но вызовы GC очень частые, иногда чаще чем раз в 10 секунд.

07-16 14:21:38.403: D/dalvikvm(16883): GC_CONCURRENT freed 1427K, 23% free 13244K/17112K, paused 105ms+7ms, total 168ms
07-16 14:21:43.578: D/dalvikvm(16883): GC_CONCURRENT freed 1807K, 22% free 13483K/17112K, paused 10ms+24ms, total 162ms
07-16 14:21:51.842: D/dalvikvm(16883): GC_CONCURRENT freed 1890K, 21% free 13539K/17112K, paused 59ms+19ms, total 156ms
07-16 14:22:02.282: D/dalvikvm(16883): GC_CONCURRENT freed 1941K, 21% free 13551K/17112K, paused 19ms+16ms, total 138ms
07-16 14:22:06.276: D/dalvikvm(16883): GC_CONCURRENT freed 2001K, 22% free 13500K/17112K, paused 6ms+4ms, total 91ms
07-16 14:22:17.287: D/dalvikvm(16883): GC_CONCURRENT freed 1878K, 21% free 13561K/17112K, paused 12ms+6ms, total 97ms
07-16 14:22:28.138: D/dalvikvm(16883): GC_CONCURRENT freed 1936K, 21% free 13562K/17112K, paused 6ms+20ms, total 104ms
07-16 14:22:35.194: D/dalvikvm(16883): GC_CONCURRENT freed 1926K, 21% free 13557K/17112K, paused 3ms+11ms, total 64ms
0
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
16.07.2013, 15:30
Здравствуйте! Я подобрал для вас темы с ответами на вопрос Оптимизация приложения. Слишком часто вызывается GC (Программирование Android):

Не вызывается onDestroy при принудительно остановке приложения - Программирование Android
Есть приложение с использованием нативной библиотеки. В onCreate вызывается метод инициализации этой библиотеки(выделяется память и тд.) ...

Ищу сотоварища для разработки не слишком сложного приложения - Программирование Android
Добрый вечер. На полном энтузиазме, для себя любимой, хочу сделать приложение. Вроде бы неплохо получается, неплохо получается, НО с...

Оптимизация приложения - Программирование Android
Здравствуйте, уважаемые форумчане, подскажите пожалуйста в трех вопросах. 1)Допустим, что приложение генерит текст из нескольких...

Оптимизация приложения - Программирование Android
Дорогие форумчане!Работаю над приложение. Его смысл в том что бы заполнять таблицу случайными полями из других таблиц. Есть таблица с...

C# оптимизация приложения под разные экраны(не GUI) - Программирование Android
Здравствуйте. Дело в том, что изначально я делал игру(2d в Unity через спрайты) под 1366x768, но при запуске на других разрешениях...

QGraphicsView слишком часто отрисовывает сцену = тормоза - C++ Qt
Не могу сообразить, как сделать так, чтобы сцена (модель) рассчитывалась часто, а представление отображало лишь отдельные изменения. По...

Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
MonStar
19 / 19 / 3
Регистрация: 10.04.2011
Сообщений: 225
17.07.2013, 00:44  [ТС] #16
Цитата Сообщение от V0v1k Посмотреть сообщение
может храните в нераспарсеном виде и парсьте когда нужно отобразить...
Не думаю что подойдет, данные приходят в виде JsonArray, при чем если один раз придет [a,b,d], то второй раз может прийти [b,d,c], а третий [a,d,c].
Да и стринги тоже объекты, они тоже будут очищаться
Цитата Сообщение от V0v1k Посмотреть сообщение
еще покажите что делает updateContent, может кто подскажет как оптимизировать чтобы меньше объектов плодилось
Он просто складывает распарсеные данные в Map и достает их, когда нужно отобразить на экран. В результате всегда имеем 100% свежие данные
Java
1
2
3
4
5
6
    public void updateContent(TickerInstrumentModel model) {
        String instrument = model.getInstrument();
        if (isNeeded(instrument)) {
            models.put(instrument, model);
        }
    }
0
V0v1k
1158 / 982 / 1
Регистрация: 28.06.2012
Сообщений: 3,462
17.07.2013, 00:48 #17
не понял почему бы просто не хранить последний JsonArray, а когда нужно будет отобразить, тогда и парсить.
или даже не JsonArray, а просто String c всем джейсоном.
0
MonStar
19 / 19 / 3
Регистрация: 10.04.2011
Сообщений: 225
17.07.2013, 00:51  [ТС] #18
Цитата Сообщение от V0v1k Посмотреть сообщение
не понял почему бы просто не хранить последний JsonArray, а когда нужно будет отобразить, тогда и парсить.
или даже не JsonArray, а просто String c всем джейсоном.
Я думал, что ответил на этот вопрос в предыдущем сообщении
JsonArray содержит данные вразнобой. Если у меня например 10 видов данных, то в одном массиве может прийти 1,2,5 а в другом 7,8,10. А какой из них мне нужно решаю уже внутри приложения. Следовательно нужно парсить, что бы посмотреть что внутри

String хранить не вижу смысла по той причине, что он в конце концов тоже будет очищаться и забираться GC, по сути тоже самое, только объект поменьше
0
V0v1k
1158 / 982 / 1
Регистрация: 28.06.2012
Сообщений: 3,462
17.07.2013, 01:01 #19
Цитата Сообщение от MonStar Посмотреть сообщение
String хранить не вижу смысла по той причине, что он в конце концов тоже будет очищаться и забираться GC, по сути тоже самое, только объект поменьше
ну, 1 объект лучше чем 100.
Цитата Сообщение от MonStar Посмотреть сообщение
JsonArray содержит данные вразнобой. Если у меня например 10 видов данных, то в одном массиве может прийти 1,2,5 а в другом 7,8,10. А какой из них мне нужно решаю уже внутри приложения. Следовательно нужно парсить, что бы посмотреть что внутри
ну так храните 10 объектов, вам же не нужно полностью пропарсить объект чтобы узнать его тип?
так где конкретно парсинг происходит покажите?

Добавлено через 2 минуты
а то написали в теме "Оптимизация приложения", а код этого приложения не показываете.
друдно что-то советовать если не видно полной картины.
0
MonStar
19 / 19 / 3
Регистрация: 10.04.2011
Сообщений: 225
17.07.2013, 01:13  [ТС] #20
Цитата Сообщение от V0v1k Посмотреть сообщение
а то написали в теме "Оптимизация приложения", а код этого приложения не показываете.
друдно что-то советовать если не видно полной картины.
Сомневаюсь, что поможет лишняя сотня классов, которая затрагивает другие части приложения. По возможности могу показать, что где происходит конечно.

Метод ниже подключается к непрерывному потоку WebSocket'а и постоянно получает строки в виде JsonArray
Java
1
2
3
4
5
6
7
8
9
10
11
public void onMessage(String message) {
        try {
            jsonArray = new JSONArray(message);
            int lenght = jsonArray.length();
            for (int i = 0; i < lenght; i++) {
                model = new TickerInstrumentModel(jsonArray.getJSONObject(i));
                tickerContent.updateContent(model);
            }
        } catch (Exception e) {
        }
    }
Сначала парсится весь Array, а потом каждый объект в отдельности. Как я сказал по задумке встроенного JSON в Android это происходит в момент создания объекта. TickerInstrumentModel - это наследник JsonObject.

Потом модель передается в управление контентом, где метод isNeeded(instrument) решает, нужно нам это или нет. Если нет то он просто отпадает, если да, то сохраняется в Map. В итоге Map хранит 50 различных объектов (ключ всегда одинаковый), но с разными данными.
Java
1
2
3
4
5
6
7
8
9
    
private Map<String, TickerInstrumentModel> models;
 
public void updateContent(TickerInstrumentModel model) {
        String instrument = model.getInstrument();
        if (isNeeded(instrument)) {
            models.put(instrument, model);
        }
    }

Затем в момент, когда потребовалось получить все данные (предыдущие закончились) вызывается такой метод
Java
1
2
3
    public void requestContent(final IContentBuildCallback callback) {
        contentBuilder.build(models, settings, callback);
    }
Он отдает Map наверх в UI и я его отображаю в виде бегущей строки.

Добавлено через 1 минуту
Цитата Сообщение от V0v1k Посмотреть сообщение
ну так храните 10 объектов, вам же не нужно полностью пропарсить объект чтобы узнать его тип?
Нужно полностью парсить обязательно, иначе не узнать что внутри


Пока писал, что-то упустил. JSON парсится в момент создания объекта на сколько я знаю. Это
Java
1
new JSONArray(message);
и
Java
1
new TickerInstrumentModel(jsonArray.getJSONObject(i));
0
V0v1k
1158 / 982 / 1
Регистрация: 28.06.2012
Сообщений: 3,462
17.07.2013, 01:22 #21
Цитата Сообщение от MonStar Посмотреть сообщение
Сомневаюсь, что поможет лишняя сотня классов
а зачем сотня классов? достаточно одного JSONObject'a.
Цитата Сообщение от MonStar Посмотреть сообщение
Java
1
new TickerInstrumentModel(jsonArray.getJSONObject(i));
покажите класс TickerInstrumentModel, не понятно что он делает с JSONObject'ом.
0
MonStar
19 / 19 / 3
Регистрация: 10.04.2011
Сообщений: 225
17.07.2013, 01:26  [ТС] #22
Java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
public class TickerInstrumentModel extends JSONObjectWrapper {
 
    private static final String PRICE = "price";
 
    public TickerInstrumentModel(JSONObject object) {
        super(object);
    }
 
    public TickerInstrumentModel(Parcel source) {
        super(source);
    }
 
    public TickerInstrumentModel(String json) {
        super(json);
    }
 
    public double getPrice() {
        return getDouble(PRICE);
    }
Java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
public class JSONObjectWrapper implements Parcelable {
    private static final String TAG = JSONObjectWrapper.class.getSimpleName();
    private JSONObject jo;
 
    public JSONObjectWrapper() {
        jo = new JSONObject();
    }
 
    public JSONObjectWrapper(JSONObject object) {
        jo = object;
    }
 
    public JSONObjectWrapper(String json) {
        try {
            jo = new JSONObject(json);
        } catch (JSONException e) {
            Log.e(TAG, "JSON Not Valid (constructor object)", e);
        }
    }
 
    protected double getDouble(String name) {
        try {
            if (isNull(name)) {
                return 0;
            }
            return jo.getDouble(name);
        } catch (JSONException e) {
            Log.e(TAG, "JSON not contain " + name, e);
        }
        return 0;
    }
 
    private boolean isNull(String name) {
        return jo.isNull(name);
    }
0
V0v1k
1158 / 982 / 1
Регистрация: 28.06.2012
Сообщений: 3,462
17.07.2013, 01:34 #23
теперь понятнее, а то я думал может у вас в конструкторе TickerInstrumentModel вытаскивается сотня полей.
на будущее: по парсингом имеется ввиду получение конечных данный, например выполнение метода getPrice.
1
MonStar
19 / 19 / 3
Регистрация: 10.04.2011
Сообщений: 225
17.07.2013, 01:35  [ТС] #24
Цитата Сообщение от V0v1k Посмотреть сообщение
теперь понятнее, а то я думал может у вас в конструкторе TickerInstrumentModel вытаскивается сотня полей.
на будущее: по парсингом имеется ввиду получение конечных данный, например выполнение метода getPrice.
За совет на будущее спасибо. А поля конечно вытаскиваются, одно, уже когда складываются в Map. Их там всего 3
0
V0v1k
1158 / 982 / 1
Регистрация: 28.06.2012
Сообщений: 3,462
17.07.2013, 01:36 #25
единственно что приходит на мой сонный ум, так это создание веб сервиса который будет принимать этот поток данных и по запросу отдавать клиенту последние данные.
0
MonStar
19 / 19 / 3
Регистрация: 10.04.2011
Сообщений: 225
17.07.2013, 01:39  [ТС] #26
Цитата Сообщение от V0v1k Посмотреть сообщение
единственно что приходит на мой сонный ум, так это создание веб сервиса который будет принимать этот поток данных и по запросу отдавать клиенту последние данные.
Думаю это слишком сложно для такой задачи. Приложение по сути делается по макету с iOS, и там с этим на сколько я знаю никаких проблем. Все JSON объекты создаются и выбрасываются в любых количествах без ущерба
0
V0v1k
1158 / 982 / 1
Регистрация: 28.06.2012
Сообщений: 3,462
17.07.2013, 01:39 #27
а то, что отсылает эти данные нельзя переделать чтобы оно само так складывало и по запросу давало все последние данные?
0
MonStar
19 / 19 / 3
Регистрация: 10.04.2011
Сообщений: 225
17.07.2013, 01:44  [ТС] #28
Цитата Сообщение от V0v1k Посмотреть сообщение
а то, что отсылает эти данные нельзя переделать чтобы оно само так складывало и по запросу давало все последние данные?
К сожалению нет, всё что со стороны сервера вне моей компетенции. Вполне может быть, что они как раз отправляются в момент обновления на сервере, но наверняка этого не могу знать.
В любом случае спасибо за терпение ) если будут идеи всегда рад. Уже третьи сутки не могу справиться с этим. Попробую искать в других местах.


И можно пару вопросов по тонкостям работы Java или Android.
1. GC_СONCURRENT останавливает всё приложение полностью или я ошибаюсь? Просто пишут что сборщик выполняется синхронно
2. Если я создам объект таким образом
Java
1
2
Object o1 = new Object(1);
o1 = new Object(2);
То я правильно понимаю, что ссылка на new Object(1) теряется, и он убирается сборщиком?

А то за время раскопок и поисков я уже ни в чем не уверен. Всю голову сломал
0
V0v1k
1158 / 982 / 1
Регистрация: 28.06.2012
Сообщений: 3,462
17.07.2013, 01:51 #29
Цитата Сообщение от MonStar Посмотреть сообщение
К сожалению нет, всё что со стороны сервера вне моей компетенции. Вполне может быть, что они как раз отправляются в момент обновления на сервере, но наверняка этого не могу знать.
В любом случае спасибо за терпение ) если будут идеи всегда рад. Уже третьи сутки не могу справиться с этим. Попробую искать в других местах.
ну, по правильному, сервер должен давать вам по запросу все нужные данные, а не слать постоянно черти что.

Цитата Сообщение от MonStar Посмотреть сообщение
1. GC_СONCURRENT останавливает всё приложение полностью или я ошибаюсь? Просто пишут что сборщик выполняется синхронно
не знаю, никогда не было с ним проблем, вот и не исследовал этот вопрос.
Цитата Сообщение от MonStar Посмотреть сообщение
То я правильно понимаю, что ссылка на new Object(1) теряется, и он убирается сборщиком?
да, правильно, но убирается не сразу же.
0
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
17.07.2013, 01:51
Привет! Вот еще темы с ответами:

Ускорить запуск часто выполняемого приложения - Windows
Всем привет. Итак есть приложение EXE (сорцов нет), используем его для внутренних нужд. Оно маленькое, около 100 кб., но запускать его...

Как в функции DLL сделанной на VB получить полное имя приложения из которого вызывается эта функция - Visual Basic
Как в одной из функций DLL, сделанной на VB, получить полное имя (и/или путь) приложения из которого вызывается эта функция ?

Оптимизация приложения - Pascal ABC
Вот собственно сам код program Figther; var q,w,e,r,t,y,u,i :integer; begin r:=25;//Жизнь kot w:=30;//Жизнь den repeat ...

Оптимизация приложения - Java
Здравствуйте! 1.В игровых приложениях для андоид(имеется ввилу 2Д игры со спрайтовой анимацией), при отрисовке экрана, приходится...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
Yandex
Объявления
17.07.2013, 01:51
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2017, vBulletin Solutions, Inc.
Рейтинг@Mail.ru