Каковы требования к продолжительности хранения временных? - PullRequest
3 голосов
/ 19 августа 2011

Рассмотрим следующий код:

class Test() {
public:
    Test()
    {
       memset( buffer, 0, sizeof( buffer ) );
    }
    void Process()
    {
       printf( buffer );
    }
private:
    char buffer[1000];
};

int main()
{
    Test().Process();
    char buffer[1000] = {};
    print( buffer );
    return 0;      
}

Я не могу определить, разрешено ли buffer в main повторно использовать память, ранее занятую временным объектом class Test.Согласно Стандартному автоматическому хранилищу (3.7.2 / 1) должно сохраняться как минимум до конца блока .

. Я не могу найти фразу, которая заставила бы временный объект использовать автоматическийхранилище, за исключением 6.6 / 2, где описан оператор перехода и говорится, что при выходе из области [...], деструкторы (12.4) вызываются для всех построенных объектов с автоматической продолжительностью хранения (3.7.2) (именованные объектыили временных) , что, по-видимому, подразумевает, что временные используют автоматическое хранение.

Требуется ли временным лицам использовать автоматическое хранение?Разрешено ли локальной переменной в main в приведенном выше коде повторно использовать память, ранее занятую временным хранилищем, или она должна использовать отдельное хранилище?

Ответы [ 5 ]

6 голосов
/ 19 августа 2011

Время жизни временного (если не связано с const&) продолжается до конца полного выражения. В вашем случае первая строка в main. Компилятору разрешено повторно использовать одну и ту же память, но независимо от того, используется она или нет, это деталь реализации (т.е. качество реализации )

12,2 [класс.время]

/ 3 [...] Временные объекты уничтожаются как последний шаг в оценке полное выражение (1.9), которое (лексически) содержит точку, где они были созданы. [...]

/ 4 Существуют два контекста, в которых временные уничтожаются в другой точке, чем конец полного выражения. Первый контекст - это когда выражение появляется как инициализатор для декларатора, определяющего объект. [...]

/ 5 Второй контекст - это когда ссылка привязана к временному.

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

3 голосов
/ 19 августа 2011

3.7.2 / 1 конкретно обсуждает переменные области видимости .У тех есть хранение, которое должно длиться блок.Однако, как вы обнаружили, временные do имеют автоматическую продолжительность хранения, но не являются переменными области действия блока .(См. 3.3.3, область видимости блока связана с именами).

2 голосов
/ 19 августа 2011

Синтаксис Test() создает временный.Это отличается от объекта с именем:

Test iHaveAName;

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

Так что, если вы сделаете Test().Process(), временный Test() будет жить достаточно долго, чтобы Process() мог закончить.

1 голос
/ 19 августа 2011

Экземпляр Test живет до тех пор, пока ;. Будет ли buffer повторно использовать хранилище, используемое для экземпляра Test, не определено. AFAIK, в стандарте нет ничего, что мешало бы компилятору повторно использовать пробел.

0 голосов
/ 19 августа 2011

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

...