Home > OS >  Are temporary variables released at the end of a statement?
Are temporary variables released at the end of a statement?

Time:12-07

I'm trying to find out when temporary variables are released. I wrote the code below.

#include <stdio.h>

class C
{
public:
    C()
    {
        printf("C O\n");
    }
    C(const C&)
    {
        printf("C& O\n");
    }
    virtual ~C()
    {
        printf("C D\n");
    }
};

int kkk(const C&)
{
    printf("kkk\n");
    return 0;
}
int kkk2(int)
{
    printf("kkk2\n");
    return 0;
}

int main()
{
    (kkk2( kkk2( (kkk(C()),3) ) ), printf("dsfsdfs\n"), true) && (printf("dsdddf\n"),true);
    printf("=====\n");
    return 0;
}

I expect Class C to be released after kkk is called, but actually, the result is:

C O
kkk
kkk2
kkk2
dsfsdfs
dsdddf
C D
=====

I run the code with g clang and msvc , the result is same. Class C is release at the end of a statement.

Is it a C standard to release temporary variables at the end of a statement?

CodePudding user response:

From Temporary_object_lifetime

All temporary objects are destroyed as the last step in evaluating the full-expression that (lexically) contains the point where they were created, and if multiple temporary objects were created, they are destroyed in the order opposite to the order of creation. This is true even if that evaluation ends in throwing an exception.

There are two exceptions from that: [..]

So to answer your question:

Is it a C standard to release temporary variables at the end of a sentence?

Yes, temporaries are destroyed at end of full-expression (not sentence).

CodePudding user response:

In C , temporary objects are normally destroyed at the end of the full-expression. Normally, this means at the end of the statement in which the temporary object is created. There are some exceptions to this rule, but they don't apply in your situation.

You may be confused by the C 98 concept of "sequence point". The comma operator and the || and && operators were sequence points in C 98, however this does not mean that temporary objects would be destroyed upon reaching one of these operators. In any case, the concept of a sequence point was abolished in C 11 (we now say "sequenced before" and "sequenced after").

CodePudding user response:

Yes, temporaries are destroyed at the end of the full expression (exceptions that don't apply here aside). Usually that is at the next ;.

If this wasnt the case it would be just too simple to write horribly wrong code. Consider this somewhat contrived example of a function that returns an iterator to a string where it finds a 'c':

#include <string>
#include <iostream>
#include <algorithm>

std::string::const_iterator find_c(const std::string& str) {
    auto it = std::find(str.begin(),str.end(),'c');
    if (it == str.end()) throw "not found";
    return it;
}

int main() {
    std::cout << *(find_c("abc"));
}

If the temporary std::string would be destroyed right after find_c returned as you expect, then find_c could not be used with temporaries, because the returned iterator can only be dereferenced while the string is still alive.

  •  Tags:  
  • c
  • Related