Intereting Posts
SINGLE_TOP | CLEAR_TOP, похоже, работает 95% времени. Почему 5%? Байт байта Android для Bitmap Как сделать Схема ввода текста в формате HTML Невозможно dlopen (libsomething.so) Невозможно загрузить библиотеку: link_image : не удалось связать libsomething.so Какие преимущества дает Maven (более муравьям) для создания проектов Android? Видео для Android HTML5 – работает при нажатии на воспроизведение, но не video.play () Код для запуска внешнего приложения явно Пользовательские хромированные вкладки требуют выбора нескольких браузеров Как показать изображения в режиме просмотра изображений в простом адаптере? Какова цель аргумента масштаба в таких функциях, как setYLabelsColor ()? Почему я получаю ошибку? Канал невосстановимо сломан и будет утилизирован! Как добавить пользовательскую панель действий с навигационным ящиком? Создание TextViews с равной шириной в строке Заголовок списка Android Складной элемент списка в навигации Ящик

Интерпретация многоуровневой трассировки производительности (Eclipse / Android)

Я работаю над игрой для Android, и я начал замечать небольшую медлительность во время разработки, поэтому я хотел попытаться использовать многопоточность для удовольствия и обучения.

Мое приложение имеет 3 потока:

  1. UI-поток (должен быть в основном бездействующим)
  2. Игровая логическая нить
  3. Графика

Я минимизировал критический раздел между потоками 2 и 3, насколько мог, с идеей, что логика игры может обновляться независимо от потока рендеринга, а затем в конце обоих потоков я мог бы иметь как можно более короткое окно, где я нажимаю все Обновления графики из логического потока в игровой цикл. Это должно позволить двум потокам работать независимо в течение большей части времени. В теории звучит как победа в производительности.

Однако, как только я добрался до реализации, моя работа заняла большое место. Это намного хуже, чем раньше, один цикл обновления и рендеринга занимает примерно 50 мс (20 кадров в секунду), поэтому он выглядит как мусор. Это всего лишь рендеринг примерно 20 треугольников и, возможно, 20 текстурированных квадрациклов, действительно простая рабочая нагрузка (я боюсь думать, что будет, когда я реализую правильную графику).

В любом случае я взял трассировку DDMS в андроиде в профиль, где дела шли неправильно или могут быть улучшены.

trace1 http://i.stack.imgur.com/DDUYE.png

Это взгляд примерно на 3 кадра моей игры. Пока это, похоже, делает то, что я ожидал. Части, выделенные синим цветом, представляют собой заблокированную секцию, которая выглядит правильно (держит glThread в основном, ожидая, пока он заблокирован). Однако как только я разблокирую его, я должен видеть, что оба потока работают одновременно, и похоже, что они есть, но если я посмотрю ближе:

trace2 http://i.stack.imgur.com/vukXQ.png

Я занимаюсь разработкой на двухъядерном телефоне, но если я правильно понял трассировку, это не похоже, что это когда-либо делает что-то параллельно, и что хуже, похоже, это переключение активного потока сотни раз за миллисекунду! (Если я не интерпретирую это неправильно). Все это переключение контекста похоже, что это было бы ужасно для производительности, поэтому я не уверен, почему он хотел бы переключаться туда и обратно так быстро.

Поэтому, после моего долгого объяснения, мне интересно несколько вещей:

  1. Правильно ли я понимаю, что заполненные прямоугольники в трассе являются активными потоками, а цветные линии – спящими потоками? Иначе что они означают?
  2. Почему я никогда не видел, чтобы мои потоки работали одновременно на якобы двухъядерном телефоне?
  3. Почему он так быстро переключает активные потоки?
  4. В DDMS я получаю предупреждение «ПРЕДУПРЕЖДЕНИЕ: активен отладчик, результаты отслеживания методов будут искажены». О чем это беспокоиться? Как я могу избавиться от этого предупреждения? (Я запускал приложение через Run, а не через Debug, если это имеет значение)

Solutions Collecting From Web of "Интерпретация многоуровневой трассировки производительности (Eclipse / Android)"

Очень хороший вопрос, позвольте мне начать с ответов:

  1. Вы перепутали нити / методы / activeMethod. Каждая строка в traceview представляет собой поток (и если вы назвали свои потоки, вы увидите, что это имя на левой стороне, например «GL Thread», «main» и т. Д.). Прямоугольники (цветные) представляют собой активные методы выполнения внутри каждого потока, в то время как цветные линии представляют собой «приостановленные» методы внутри потока. Под «приостановкой» я имею в виду, что «метод все еще выполняется, но контекст был переключен на какой-то другой поток, и когда контекст снова переключился на этот поток, этот метод будет продолжать работать. В терминологии, которую вы использовали в своем вопросе, Линии – это методы спящего потока, а прямоугольник – активный метод выполнения потоков. Более подробную информацию о отслеживании DDMS можно найти здесь .
  2. Распределение потоков между ядрами – это еще одна история и в значительной степени зависит от основных механизмов ОС Android. Прежде всего, убедитесь, что целевая ОС Android запущена с параметром SMP (Symmetric Multi-Processing), который используется по умолчанию для многоядерных телефонов, я думаю :), но я не разбираюсь в этих вещах. Несколько слов о SMP вы можете найти здесь .
  3. Переключение потоков зависит от OS Thread / Process scheduler, приоритета потока и т. Д. Более подробную информацию об этом можно найти в этом ответе.
  4. Даже если вы запустили приложение в режиме без отладки, когда вы подключаетесь к DDMS и выполняете такие функции, как профилирование методов, вы активируете отладочные части davlik vm. Подробнее об отладке см. Раздел «Реализация».

Надеюсь, вы найдете этот ответ полезным.

Спасибо за вопрос. Мне также будет полезен полный ответ инсайдера. Я скажу то, что знаю.

  • Некоторые (все?) Телефоны имеют возможность включить / отключить второе ядро. Вы проверили, что ваш включен?

  • В моем собственном приложении я заметил, что просто переход от одного потока к другому (на одном ядре) без изменения общей работы, вызвавшей замедление роста в 1,5 раза, так что сама по себе резьба имеет стоимость.

  • В новостях говорилось, что Intel вызывается Google из-за плохой реализации многоядерных потоков:

    http://www.pcworld.com/article/257307/dual_core_processors_wasted_on_android_intel_claims.html

    Ваши результаты подтверждают это.

  • Еще одна вещь, о которой нужно помнить, заключается в том, что многоядерный процессор не является многопроцессорным. Вы используете пропускную способность кэша и контроллера памяти между ядрами. Можно остановиться, пока он ждет, пока другой закончит с общим ресурсом, в частности, для записи в общих строках кэша. Однако этот эффект не должен учитывать однопоточность, которую вы видите.