namespace and global function

J

Jayden Shui

Hello All,

I have a global function to clone an object.

template<class T>
T* Clone(T const& t)
{
return new T(t);
}

and I have a class A in a namespace S which needs a specialized Clone
function

namespace S {

class A
{
friend A* Clone(A const& a)
{
// do something special
return new A(a);
}
};

};

The clone function for S::A is introduced in the namespace S, that is
S::Clone. It is not in the global scope. Is there any way to introduce
it in the global scope while still keeping the function body in the
namespace scope.

Thank you very much for your kind help!

Best regards,

Jayden
 
J

Joshua Maurice

Hello All,

I have a global function to clone an object.

template<class T>
T* Clone(T const& t)
{
    return new T(t);

}

and I have a class A in a namespace S which needs a specialized Clone
function

namespace S {

class A
{
    friend A* Clone(A const& a)
    {
        // do something special
        return new A(a);
    }

};
};

The clone function for S::A is introduced in the namespace S, that is
S::Clone. It is not in the global scope. Is there any way to introduce
it in the global scope while still keeping the function body in the
namespace scope.

Yes. A using declaration in global scope.
using S::Clone;

Also, IIRC a friend declaration in a class doesn't inject the name
into the surrounding scope, so that using declaration will fail.
Instead, you need the following (at global scope):
namespace S { A* Clone(A const& a); }
using S::Clone;

I'd suggest googling Argument Dependent Lookup (ADL) aka Koenig
lookup, as that was meant to solve this problem.
 
S

SG

I have a global function to clone an object.

template<class T>
T* Clone(T const& t)
{
    return new T(t);
}

and I have a class A in a namespace S which needs a specialized Clone
function

namespace S {

class A
{
    friend A* Clone(A const& a)
    {
        // do something special
        return new A(a);
    }
};
}

The clone function for S::A is introduced in the namespace S,
that is S::Clone.

That's not true. Clone is not injected into the namespace S. But it
can be found via ADL (argument dependent lookup).
It is not in the global scope. Is there any way to introduce
it in the global scope while still keeping the function body in the
namespace scope.

Why? Isn't ADL not enough for you? Just use "Clone" unqualified. If
you want to fall back on your global template you can do so with a
using declaration just to be safe

namespace funky {

template<class T>
class indirect_value {
T* ptr_;
public:
:::

indirect_value(indirect_value const& x)
: ptr_(0) {
using ::Clone; // to avoid hiding issues with other, unrelated
Clone functions
ptr_ = Clone(*x.ptr_); // ADL is applicable, falls back
on ::Clone
}

:::
};

}

You should understand how unqualified name lookup works.

Cheers!
SG
 
A

Alf P. Steinbach

I have a global function to clone an object.

template<class T>
T* Clone(T const& t)
{
return new T(t);
}

This will use the statically known type, so if T is polymorphic it may
not necessarily clone in the conventional meaning of the word as
creating a copy.

Rather, when the dynamic type of `t` is a subclass of T, you'll get a slice.

That's why 'clone' is usually a virtual member function.


Cheers & hth.,

- Alf
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,965
Messages
2,570,148
Members
46,710
Latest member
FredricRen

Latest Threads

Top