
Andrey Semashev wrote:
Consider the following examples:
Example 1:
void foo(std::set< int >& my_set) { bool commit = false; std::set< int >::iterator it = my_set.insert(10); BOOST_SCOPE_EXIT((my_set)(it)(commit)) { // Which one will be erased here? // Not necessarily the one we intended to.
Sorry for such late response. Can you explain what is intended value of it?
if (!commit) my_set.erase(it); } BOOST_SCOPE_EXIT_END
// Do smth. with "it"
it = my_set.find(5); // and reuse it
// Do smth. with "it" again
commit = true; }
Example 2:
class A { int m_i;
void foo() { m_i = 1; BOOST_SCOPE_EXIT((m_i)) { // What's the value of m_i here? std::cout << m_i << std::endl; } BOOST_SCOPE_EXIT_END
bar(); }
I believe BOOST_SCOPE_EXIT should be moved to the end of foo(). I am thinking about BOOST_SCOPE_EXIT as of try/finally with different layout of braces: void baz() { // 0 try { // 1 foo(); } // 2 finally { // 3 bar(); } // 4 } // 5 void baz() { // 0 and 1 foo(); BOOST_SCOPE_EXIT() { // 3 bar(); } // 4 BOOST_SCOPE_EXIT_END } // 5 and 2
// Assume that bar's implementation is somewhere far away void bar(); };
These are just illustrations, I understand that I could have created copies of the needed variables on the stack. But I think this should be the default behavior of the library, and passing by reference should be an available option.
[snip]