Я пишу небольшую библиотеку для разреженных матричных вычислений, чтобы научить себя наилучшим образом использовать объектно-ориентированное программирование. Я очень много работал над созданием хорошей объектной модели, в которой части (разреженные матрицы и графики, описывающие их структуру связности) очень слабо связаны. На мой взгляд, код гораздо более расширяемый и поддерживаемый для него.
Тем не менее, это также несколько медленнее, чем если бы я использовал тупой подход. Чтобы проверить компромисс между наличием этой объектной модели, я написал новый тип разреженной матрицы, который нарушил инкапсуляцию базового графа, чтобы увидеть, насколько быстрее он будет работать.
Сначала это выглядело довольно мрачно; код, которым я когда-то гордился, работал на 60% медленнее, чем версия без элегантного программного дизайна. Но я смог сделать несколько низкоуровневых оптимизаций - встроить функцию и чуть-чуть изменить цикл - вообще не меняя API. С этими изменениями теперь это только на 20% медленнее, чем у конкурентов.
Что приводит меня к моему вопросу: какую часть потери производительности я должен принять, если это означает, что у меня есть хорошая объектная модель?
источник
Ответы:
Очень немногие разработчики научного программного обеспечения понимают хорошие принципы проектирования, поэтому я прошу прощения, если этот ответ будет несколько затуманенным. С точки зрения разработки программного обеспечения цель научного разработчика программного обеспечения состоит в том, чтобы разработать решение, которое удовлетворяет ряду ограничений, которые часто противоречат друг другу .
Вот несколько типичных примеров этих ограничений, которые могут быть применены к дизайну вашей библиотеки разреженных матриц:
Ученые постепенно обращают больше внимания на некоторые другие общие требования от разработки программного обеспечения:
Вам может понадобиться более или менее одно из этих требований. Если вы пытаетесь выиграть приз Гордона Белла за результативность, тогда важны даже доли процента, и лишь немногие судьи будут оценивать качество вашего кода (при условии, что вы сможете убедить их, что это правильно). Если вы пытаетесь оправдать выполнение этого кода на общем ресурсе, таком как кластер или суперкомпьютер, вам часто приходится отстаивать претензии по поводу производительности вашего кода, но они редко бывают очень строгими. Если вы пытаетесь опубликовать в журнале статью, в которой рассказывается о повышении производительности вашего подхода, то вам нужно быть на законных основаниях быстрее, чем ваши конкуренты, а производительность в 20% - это компромисс, который я бы с удовольствием сделал для лучшей ремонтопригодности и повторного использования.
Возвращаясь к вашему вопросу, «хороший дизайн», предоставленный достаточно времени для разработки, никогда не должен жертвовать производительностью. Если цель состоит в том, чтобы сделать код, который выполняется как можно быстрее, код должен быть разработан с учетом этих ограничений. Вы можете использовать такие методы, как генерация кода, встроенная сборка, или воспользоваться хорошо настроенными библиотеками, чтобы помочь вам решить вашу проблему.
Но что, если вам не хватает времени на разработку? Что достаточно хорошо? Ну, это зависит, и никто не сможет дать вам хороший ответ на этот вопрос без дополнительного контекста.
FWIW: Если вы действительно заинтересованы в написании высокопроизводительных ядер с разреженной матрицей, вам следует сравнить их с оптимизированной установкой PETSc и работать с их командой, если вы победите их, они будут рады включить настроенные ядра в библиотеку.
источник
Вопрос в том, на что ты тратишь время. Для большинства из нас мы тратим 3/4 времени на программирование и 1/4 времени на ожидание результатов. (Ваши цифры могут отличаться, но я думаю, что число не совсем без достоинств.) Итак, если у вас есть дизайн, который позволил вам программировать вдвое быстрее (3/4 единицы времени вместо 1,5 единицы времени), то вы Можно увеличить производительность на 300% (от 1/4 до 1 единицы времени), и вы по-прежнему впереди в плане реального времени, потраченного на решение проблемы.
С другой стороны, если вы выполняете тяжелые вычисления, ваши вычисления могут выглядеть иначе, и вам может потребоваться больше времени для оптимизации кода.
Мне 20% кажется довольно хорошим компромиссом, если вы в конечном итоге будете более продуктивными.
источник
ИМХО штраф до 50% (по любой причине) не так уж и плох.
На самом деле я видел разницу в производительности на 0-30% только в зависимости от типа компилятора. Это для разреженной процедуры MatScult в PETSc на матрицах, возникающих из дискретизации FE низкого порядка.
источник
Дизайн программного обеспечения не будет автоматически улучшаться с течением времени. Производительность будет. Вы получите 20% с вашим следующим процессором. Кроме того, хороший дизайн программного обеспечения облегчит расширение или улучшение библиотеки в будущем.
источник
Общий принцип - сначала пойти на хороший дизайн, а затем оптимизировать производительность только при необходимости . Сценарии использования, в которых действительно требуется увеличение производительности на 20%, могут быть довольно редкими, если они вообще подходят.
источник