views:

139

answers:

2
template<class Y>

operator auto_ptr_ref<Y>() throw() {

   return auto_ptr_ref<Y>(release());
}

It is part of implementation of class auto_ptr in standard library.

What does this means to do?

Why there is an "auto_ptr_ref" between "operator" and "()"?

+1  A: 

That is the conversion operator in action, casting from auto_ptr to auto_ptr_ref<Y>.

sixlettervariables
Cast operator is a synonym for conversion operator.
Dean Michael
@Dean Michael: thanks, hard to break C'isms
sixlettervariables
+2  A: 

I'll tell you why that conversion operator happens to be there. Well, look at this example:

struct A;
struct B {
    explicit B(A&a):a(a){ }   
    A &a;
};

struct A {
    A() { }
    A(B b){ move_from(a); }
    A(A &a) { move_from(a); }

    operator B() { return B(*this); }

    void move_from(A &a) { 
        std::cout << "A::A(@" << &b.a << ")" << std::endl;
    }
};

int main() {
    A a = A();
}

We have move semantics for our class A: In its copy constructor, we want to "steal" away some stuff from the other instance. For auto_ptr, that is the pointer that is managed, for us we just output a message instead. What is important is that we can't use a usual copy constructor:

A(A const& a) { 
    /* oops, a is const, we can't steal something from it! */ 
}

But if we change that to A(A &a), we won't be able to construct from a by-value/temporary A: Those can't be bound to a reference-to-nonconst:

A(A &a) { 

}

...
A a = A(); // fail, because A &a = A() doesn't work

auto_ptr and our A class uses the trick that non-const member functions can still be called on temporaries/by-value A's. That is, we could also have written:

struct A {
    ...
    B get_b() { return B(*this); } 
    ...
};

...
A a = A().get_b();

But that works, we don't want to be bothered with that, of course. We want that it just works to assign a A() or the return value of a function returning an A by-value. So what auto_ptr and our A class uses is a conversion operator, which automatically figures out that when A is converted to B, then we could construct a A instance using the B we created temporarily.

Johannes Schaub - litb