Template functions in namespace cause errors

前端 未结 2 790
失恋的感觉
失恋的感觉 2021-01-02 10:53

Assume the following code:

#include 

template
struct Link
{
    Link(T&& val) : val(std::forward(val)) {}         


        
2条回答
  •  离开以前
    2021-01-02 11:40

    This problem is a result of an issue with the point of declaration (1) combined with dependent name lookup (2).

    (1) In the declaration

    template
    constexpr auto RemoveLinks(const Link& link) -> decltype(RemoveLinks(link.val))
    

    the name RemoveLinks, or more precisely, this overload of RemoveLinks, is only visible after the complete declarator according to [basic.scope.pdecl]/1. The trailing-return-type is part of the declarator as per [dcl.decl]/4. Also see this answer.

    (2) In the expression RemoveLinks(link.val), the name RemoveLinks is dependent as per [temp.dep]/1, as link.val is dependent.

    If we now look up how dependent names are resolved, we find [temp.dep.res]:

    In resolving dependent names, names from the following sources are considered:

    • Declarations that are visible at the point of definition of the template.
    • Declarations from namespaces associated with the types of the function arguments both from the instantiation context and from the definition context.

    The first bullet doesn't find the second overload of RemoveLinks because of the point of declaration (1). The second one doesn't find the overload because the namespace Util is not associated with any argument. This is why putting everything in the global namespace or in the namespace Util works as expected (Live example).

    For the same reason, using a qualified-id in the trailing-return-type (like -> decltype(Util::RemoveLinks(link.val)) doesn't help here.

提交回复
热议问题