20% снижение производительности за хороший дизайн программного обеспечения


17

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

Тем не менее, это также несколько медленнее, чем если бы я использовал тупой подход. Чтобы проверить компромисс между наличием этой объектной модели, я написал новый тип разреженной матрицы, который нарушил инкапсуляцию базового графа, чтобы увидеть, насколько быстрее он будет работать.

Сначала это выглядело довольно мрачно; код, которым я когда-то гордился, работал на 60% медленнее, чем версия без элегантного программного дизайна. Но я смог сделать несколько низкоуровневых оптимизаций - встроить функцию и чуть-чуть изменить цикл - вообще не меняя API. С этими изменениями теперь это только на 20% медленнее, чем у конкурентов.

Что приводит меня к моему вопросу: какую часть потери производительности я должен принять, если это означает, что у меня есть хорошая объектная модель?


Какую разреженную матричную операцию вы измеряли?
Билл Барт

Матрица-вектор умножается. Матрицы в диапазоне размеров от . Я сделал их графом Лапласа для случайных графов Эрдоша-Реньи со средней степенью d = log 2 n . Кроме того, показатель 20% ухудшается на некоторых машинах, так что теперь я более склонен выбросить все это. Глубокий вздохNзнак равно1024,,,,,16384dзнак равножурнал2N
Даниэль Шаперо

3
Какой язык программирования вы используете? Как правило, что-то вроде C ++ позволит вам уйти с элегантным (ish) дизайном при низкой (или несуществующей) стоимости. В других языках без метапрограммирования (Java, Fortran и т. Д.) Стоимость в 20% кажется разумной.
Л.Клевин

Можете ли вы показать нам свой код? Какой язык вы использовали? Какой компилятор и флаги компиляции? Вы нашли именно то, откуда бьет производительность? Как вы убедились, что нашли правильную причину? Какой профилировщик вы использовали и как вы его использовали? Вы уверены, что хорошая объектная модель не реализована неэффективно? 20% - это достаточно мало, так что вам нужно собрать много данных и провести подробный анализ, прежде чем сказать, что это определенно связано с дизайном, а не, скажем, с плохой реализацией или другими проблемами кодирования.
Кирилл

Короткое замечание: кажется, что все публично хвалят хороший дизайн, а не просто производительность (конечно, по очень веским причинам). Но тогда, почему так много кода реального мира действительно, действительно не поддерживается? Чувствуют ли себя все кодовые сбои виновными и, следовательно, публично молчаливыми?
AlexE

Ответы:


9

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

Вот несколько типичных примеров этих ограничений, которые могут быть применены к дизайну вашей библиотеки разреженных матриц:

  • Завершено за один месяц
  • Работает правильно на вашем ноутбуке и нескольких рабочих станциях
  • Работает эффективно

Ученые постепенно обращают больше внимания на некоторые другие общие требования от разработки программного обеспечения:

  • Документация (руководство пользователя, учебник, комментирование кода)
  • Ремонтопригодность (контроль версий, тестирование, модульная конструкция)
  • Возможность повторного использования (модульная конструкция, «гибкость»)

Вам может понадобиться более или менее одно из этих требований. Если вы пытаетесь выиграть приз Гордона Белла за результативность, тогда важны даже доли процента, и лишь немногие судьи будут оценивать качество вашего кода (при условии, что вы сможете убедить их, что это правильно). Если вы пытаетесь оправдать выполнение этого кода на общем ресурсе, таком как кластер или суперкомпьютер, вам часто приходится отстаивать претензии по поводу производительности вашего кода, но они редко бывают очень строгими. Если вы пытаетесь опубликовать в журнале статью, в которой рассказывается о повышении производительности вашего подхода, то вам нужно быть на законных основаниях быстрее, чем ваши конкуренты, а производительность в 20% - это компромисс, который я бы с удовольствием сделал для лучшей ремонтопригодности и повторного использования.

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

Но что, если вам не хватает времени на разработку? Что достаточно хорошо? Ну, это зависит, и никто не сможет дать вам хороший ответ на этот вопрос без дополнительного контекста.

FWIW: Если вы действительно заинтересованы в написании высокопроизводительных ядер с разреженной матрицей, вам следует сравнить их с оптимизированной установкой PETSc и работать с их командой, если вы победите их, они будут рады включить настроенные ядра в библиотеку.


Мне любопытно о генераторах кода - я думаю, что они могут быть полезны для меня, но я обеспокоен тем, что их будет сложно поддерживать. Я знаю, что Java-программисты часто их используют, но они часто адаптированы для генерации кода для конкретных приложений. Знаете ли вы какие-либо научные коды, которые их используют?
Даниэль Шаперо

ATLAS, FFTW, Spiral, OSKI, Ignition, stencil_codegen, чтобы назвать несколько. Это не публично рекламируется, но я не удивлюсь, если несколько важных ядер в MKL и ESSL будут сгенерированы таким образом. Написание поддерживаемого кода генерации ядра было бы интересным последующим вопросом. У меня есть опыт в этом, но я не считаю себя авторитетом.
Арон Ахмадиа

12

Вопрос в том, на что ты тратишь время. Для большинства из нас мы тратим 3/4 времени на программирование и 1/4 времени на ожидание результатов. (Ваши цифры могут отличаться, но я думаю, что число не совсем без достоинств.) Итак, если у вас есть дизайн, который позволил вам программировать вдвое быстрее (3/4 единицы времени вместо 1,5 единицы времени), то вы Можно увеличить производительность на 300% (от 1/4 до 1 единицы времени), и вы по-прежнему впереди в плане реального времени, потраченного на решение проблемы.

С другой стороны, если вы выполняете тяжелые вычисления, ваши вычисления могут выглядеть иначе, и вам может потребоваться больше времени для оптимизации кода.

Мне 20% кажется довольно хорошим компромиссом, если вы в конечном итоге будете более продуктивными.


Хороший ответ, я бы также добавил важность, где производительность имеет значение. Данный научный код не выполняет только матричное умножение; если 20% времени выполнения у вас в матричном умножении, то прирост производительности на 20% - разница всего 4%, и я с удовольствием воспользуюсь этим в обмен на более простую в использовании библиотеку.
Аврелий

1
А лучше написанная библиотека означает меньше ошибок, так что вы тратите меньше времени на ожидание неверных результатов.
Davidmh

4

ИМХО штраф до 50% (по любой причине) не так уж и плох.

На самом деле я видел разницу в производительности на 0-30% только в зависимости от типа компилятора. Это для разреженной процедуры MatScult в PETSc на матрицах, возникающих из дискретизации FE низкого порядка.


1

Дизайн программного обеспечения не будет автоматически улучшаться с течением времени. Производительность будет. Вы получите 20% с вашим следующим процессором. Кроме того, хороший дизайн программного обеспечения облегчит расширение или улучшение библиотеки в будущем.


Я не думаю, что это ответ на вопрос.
Никогуаро

0

Общий принцип - сначала пойти на хороший дизайн, а затем оптимизировать производительность только при необходимости . Сценарии использования, в которых действительно требуется увеличение производительности на 20%, могут быть довольно редкими, если они вообще подходят.

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.