Может ли доступ к неинициализированным значениям привести к снижению производительности?

Я оптимизирую матричную числовую точку доступа.

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

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

Я не делаю пилинг по нескольким причинам:

  • Лень
  • Падение производительности из-за очень плохой локализации отслаивающегося бордюра.
  • Чтобы избежать сложного кода очистки границ.

Однако мне интересно, действительно ли эти переполненные доступы, которые касаются неинициализированных значений, вызовут снижение производительности?

Я предсказуемо знаю, где происходит неинициализированный доступ, и о них также сообщается через valgrind. Я также профилировал код с помощью Intel VTune и не обнаружил никаких признаков, указывающих на снижение производительности из-за этого.


person SkyWalker    schedule 14.08.2012    source источник
comment
+1, я настоятельно рекомендую вам хотя бы инициализировать их нулями. Если вы работаете с числами с плавающей запятой, неинициализированные данные с высокой вероятностью будут денормализованы. И вы не хотите, чтобы это испортило вашу работу.   -  person Mysticial    schedule 14.08.2012
comment
Я знаю, но жадно обнулять пул предварительно выделенных матриц с помощью memset тоже очень дорого.   -  person SkyWalker    schedule 14.08.2012
comment
Хотя в зависимости от того, насколько велики ваши циклы, штраф в несколько сотен циклов в конце каждого цикла, вероятно, не заметен.   -  person Mysticial    schedule 14.08.2012
comment
Вам не нужно инициализировать весь набор данных. Только конечные точки.   -  person Mysticial    schedule 14.08.2012
comment
но вопрос больше в том, получу ли я удар по производительности, коснувшись неинициализированных значений ... пара ошибок в valgrind на самом деле меня не беспокоит, если только не будет падения производительности для доступа к неинициализированным значениям.   -  person SkyWalker    schedule 14.08.2012
comment
Загрузка неинициализированных значений не повлияет на производительность. Но если вы попытаетесь произвести над ними какие-либо арифметические действия, то это точно повредит, так как они получатся денормализованными.   -  person Mysticial    schedule 14.08.2012
comment
Хорошо, теперь понял, спасибо :) прочитал ваш пост, очень приятно!   -  person SkyWalker    schedule 14.08.2012
comment
@Mystical, если вы опубликуете ответ (даже небольшой), я приму его ... Я убежден в вашем аргументе о денормализованном флопе, поэтому я отключу призрачный слой   -  person SkyWalker    schedule 14.08.2012


Ответы (1)


Просто чтобы убрать педантичные вещи:

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


Если вы имеете дело с целыми числами, доступ к неинициализированным данным и работа с ними не повлияют на производительность. (кроме деления, все операции обычно имеют фиксированную задержку)

Для операций с плавающей запятой есть две проблемы:

  1. Сигнализация NaN
  2. Денормализованные значения

В зависимости от среды сигнализация NaN может вызвать аппаратное исключение. Так что на самом деле это будет проблема корректности, а не только проблема производительности.

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

И вы действительно не хотите возиться с денормализованными числами с плавающей запятой.

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

Тем не менее, почему неинициализированные данные склонны к денормализации? Если первые несколько битов значения с плавающей запятой равны нулю, то оно денормализовано. Это так просто. Если данные раньше были целым числом или 64-битным указателем... Они будут денормализованы при переинтерпретации как значения с плавающей запятой.


Предложения:

  • Ноль инициализирует данные. Если это слишком дорого, по крайней мере, инициализируйте конечные точки нулями.
  • Избегайте доступа к неинициализированным данным, вставив этот код очистки. Может подойти что-то вроде Duff's Device. Хотя я обычно предпочитаю набор двоичных сокращений if-операторов.
person Mysticial    schedule 14.08.2012