namespace and global function

Discussion in 'C++' started by Jayden Shui, Nov 17, 2011.

  1. Jayden Shui

    Jayden Shui Guest

    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
    Jayden Shui, Nov 17, 2011
    #1
    1. Advertising

  2. On Nov 17, 2:09 pm, Jayden Shui <> wrote:
    > 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.
    Joshua Maurice, Nov 17, 2011
    #2
    1. Advertising

  3. Jayden Shui

    SG Guest

    On Nov 17, 11:09 pm, Jayden Shui wrote:
    >
    > 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
    SG, Nov 18, 2011
    #3
  4. On 17.11.2011 23:09, Jayden Shui wrote:
    >
    > 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
    Alf P. Steinbach, Nov 18, 2011
    #4
    1. Advertising

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

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Èý¹â
    Replies:
    1
    Views:
    565
    William F. Robertson, Jr.
    Jul 29, 2003
  2. Replies:
    0
    Views:
    5,127
  3. Anonymous
    Replies:
    3
    Views:
    529
    Ron Natalie
    Aug 18, 2003
  4. Jason Heyes
    Replies:
    1
    Views:
    448
    Woebegone
    Nov 19, 2004
  5. parmenides
    Replies:
    1
    Views:
    160
    Stefan Ram
    Aug 21, 2013
Loading...

Share This Page