Topic: unnecessary ambiguities, smart pointers, implicit conversion,
Author: SG <s.gesemann@gmail.com>
Date: Fri, 20 Mar 2009 02:08:17 CST Raw View
On 19 Mrz., 00:31, ymett <ymett.on.use...@gmail.com> wrote:
> In fact, N2798 2.8.13.2.1p19 says:
> shared_ptr(const shared_ptr& r);
> template<class Y> shared_ptr(const shared_ptr<Y>& r);
>
> Requires: The second constructor shall not participate in the overload
> resolution unless Y* is implicitly convertible to T*.
Thanks for pointing this out. This part looks like a pre-concepts
version that is open to the use of SFINAE to achieve the mentioned
effect.
Howard Hinnant confirmed in a private conversation that work is
underway to "conceptize" many parts of the library.
Cheers!
SG
--
[ comp.std.c++ is moderated. To submit articles, try just posting with ]
[ your news-reader. If that fails, use mailto:std-c++@netlab.cs.rpi.edu]
[ --- Please see the FAQ before posting. --- ]
[ FAQ: http://www.comeaucomputing.com/csc/faq.html ]
Author: SG <s.gesemann@gmail.com>
Date: Tue, 17 Mar 2009 14:45:24 CST Raw View
Hi!
When it comes to implicit pointer conversions
T* --> const T*,
T* --> U* (for T derived from U)
the library supplied smart pointers (as currently defined) don't
behave as good as they could in comparison to raw pointers with
respect to overload resolution. Example:
#include <tr1/memory>
struct Foo {};
struct Bar {};
struct No {
explicit No(const std::tr1::shared_ptr<const Foo> &) {}
explicit No(const std::tr1::shared_ptr<const Bar> &) {}
};
int main() {
Foo foo(std::tr1::shared_ptr<Bar>(new Bar));
}
Source: http://ciaranm.wordpress.com/2008/12/15/c-overload-resolution-hate/
(presented with slight modifications for increased readability)
The above code doesn't compile because of an ambiguity. This
ambiguity exists because both constructors of class No are candidates
even though the instantiation of the templated shared_ptr constructor
for a conversion from shared_ptr<Bar> to shared_ptr<const Foo> would
fail at compile-time.
In this regard the smart pointers don't behave like their raw pointer
counterparts.
Wouldn't it make sense to employ SFINAE or alternativly replace the
unrestricted constructor templates of shared_ptr with restricted
templates and therefore avoid unnecessary ambiguities?
template<class T> class shared_ptr {
...
template<class Y, class D>
requires Convertible<T*,Y*> // <-- new
explicit shared_ptr(Y* p, D d);
...
template<class Y>
requires Convertible<T*,Y*> // <-- new
shared_ptr(const shared_ptr<Y>& r);
...
};
The same applies to weak_ptr and unique_ptr.
Cheers!
SG
--
[ comp.std.c++ is moderated. To submit articles, try just posting with ]
[ your news-reader. If that fails, use mailto:std-c++@netlab.cs.rpi.edu]
[ --- Please see the FAQ before posting. --- ]
[ FAQ: http://www.comeaucomputing.com/csc/faq.html ]
Author: ymett <ymett.on.usenet@gmail.com>
Date: Wed, 18 Mar 2009 17:31:09 CST Raw View
On Mar 17, 10:45 pm, SG <s.gesem...@gmail.com> wrote:
> Hi!
>
> When it comes to implicit pointer conversions
>
> T* --> const T*,
> T* --> U* (for T derived from U)
>
> the library supplied smart pointers (as currently defined) don't
> behave as good as they could in comparison to raw pointers with
> respect to overload resolution. Example:
>
> #include <tr1/memory>
>
> struct Foo {};
>
> struct Bar {};
>
> struct No {
> explicit No(const std::tr1::shared_ptr<const Foo> &) {}
> explicit No(const std::tr1::shared_ptr<const Bar> &) {}
> };
>
> int main() {
> Foo foo(std::tr1::shared_ptr<Bar>(new Bar));
> }
>
> Source:http://ciaranm.wordpress.com/2008/12/15/c-overload-resolution-hate/
> (presented with slight modifications for increased readability)
>
> The above code doesn't compile because of an ambiguity. This
> ambiguity exists because both constructors of class No are candidates
> even though the instantiation of the templated shared_ptr constructor
> for a conversion from shared_ptr<Bar> to shared_ptr<const Foo> would
> fail at compile-time.
>
> In this regard the smart pointers don't behave like their raw pointer
> counterparts.
>
> Wouldn't it make sense to employ SFINAE or alternativly replace the
> unrestricted constructor templates of shared_ptr with restricted
> templates and therefore avoid unnecessary ambiguities?
In fact, N2798 2.8.13.2.1p19 says:
<quote>
shared_ptr(const shared_ptr& r);
template<class Y> shared_ptr(const shared_ptr<Y>& r);
Requires: The second constructor shall not participate in the overload
resolution unless Y* is implicitly convertible to T*.
</quote>
and 2.8.13.3.1p4 says:
<quote>
weak_ptr(const weak_ptr& r);
template<class Y> weak_ptr(const weak_ptr<Y>& r);
template<class Y> weak_ptr(const shared_ptr<Y>& r);
Requires: The second and third constructors shall not participate in
the overload resolution unless Y* is implicitly convertible to T*.
</quote>
which is what you want. However, there are other constructors for
shared_ptr which don't have this wording, and unique_ptr doesn't
mention it at all.
Yechezkel Mett
--
[ comp.std.c++ is moderated. To submit articles, try just posting with ]
[ your news-reader. If that fails, use mailto:std-c++@netlab.cs.rpi.edu]
[ --- Please see the FAQ before posting. --- ]
[ FAQ: http://www.comeaucomputing.com/csc/faq.html ]