elision — показать, где создаются временные фильтры в Stack Overflow

Какой самый быстрый способ узнать, где создаются временные файлы в моем коде C ++?

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

Я экспериментировал с godbolt.org и это фантастика. К сожалению, это часто скрывает деревья за древесиной ассемблера, когда речь идет о временных. Кроме того, агрессивные опции оптимизации компилятора делают ассемблер полностью нечитаемым.

Есть ли другие способы сделать это?

4

Решение

«Оптимизация компилятора может дополнительно устранить временные потери».

Кажется, у вас есть небольшое неправильное понимание семантики C ++. Стандарт C ++ говорит о временных временах для определения формальной семантики программы. Это компактный способ описания большого набора возможных исполнений.

Настоящий компилятор не должен вести себя так. И часто они не будут. Реальные компиляторы знают о регистрах, настоящие компиляторы не делают вид, что POD имеют (тривиальные) конструкторы и деструкторы. Это происходит уже до оптимизации. Я не знаю ни одного компилятора, который будет генерировать тривиальные ctors в режиме отладки.

Теперь некоторая семантика, описанная в Стандарте, может быть достигнута только в достаточно близком приближении. Когда деструкторы имеют видимые побочные эффекты (подумайте std::cout), временные типы этих типов не могут быть полностью устранены. Но настоящие компиляторы могут реализовать видимый побочный эффект, не выделяя никакого хранилища. Понятие временного существования или несуществования является бинарным представлением, и в действительности существуют промежуточные формы.

4

Другие решения

Из-за правила «как если бы», вероятно, ненадежно пытаться просмотреть процесс компиляции, чтобы увидеть, где создаются временные файлы.

Но чтение кода (и кодирование) с учетом следующего параграфа стандарта может помочь определить, где создаются временные фильтры, [Class.temporary] / 2

Материализация временного объекта обычно задерживается как можно дольше, чтобы избежать создания ненужных временных объектов. [Примечание: временные объекты материализуются:

  • при привязке ссылки к prvalue ([dcl.init.ref], [expr.type.conv], [expr.dynamic.cast], [expr.static.cast], [expr.const.cast], [expr] .бросать]),

  • при выполнении доступа члена к классу prvalue ([expr.ref], [expr.mptr.oper]),

  • при выполнении преобразования массива в указатель или подписки на значение массива,

  • при инициализации объекта типа std :: initializer_list из списка braced-init-list ([dcl.init.list]),

  • для некоторых неоцененных операндов ([expr.typeid], [expr.sizeof]) и

  • когда значение prvalue появляется как выражение отброшенного значения.

В этом абзаце, исходя из стандарта C ++ 17, термин prvalue имеет новое определение [Basic.lval] / 1:

Значение prvalue — это выражение, оценка которого инициализирует объект или битовое поле или вычисляет значение операнда оператора, как определено контекстом, в котором оно появляется.

И в последнем стандарте (до C ++ 20) абзац [basic.lval] был перемещен в Выражения [expr], так что то, что мы знали как ценностные категории, развивается, чтобы стать категориями выражений.

2

По вопросам рекламы [email protected]