开发者

typedef resolution across namespaces

开发者 https://www.devze.com 2023-02-11 08:24 出处:网络
I am currently confused with the way \"using (namespace)\" statements work in C++. I have: //somewhere in included headers

I am currently confused with the way "using (namespace)" statements work in C++.

I have:

//somewhere in included headers
typedef unsigned int uint;

namespace mine {
    typedef unsigned int uint;
}
namespace other {
    using namespace mine;
    void foobar () {
        uint offender = i;
    }
}

Results in (paraphrased):

reference to 'uint' is ambiguous. candidates are

typedef unsigned int uint

and

typedef unsigned int mine::uint

Meanwhile, when I do

namespace other {
    using namespace 开发者_开发百科mine;
    using mine::uint;

    void foobar () {
        uint offender = i;
    }
}

Everything works fine. It seems strange to me that "using identifier;" changes the visibility of other typedef definition (conceals the global one?). Can someone point me to what kind of rules in C++ govern resolution of typedefs across namespaces?


A name made visible by a using-directive appears in the nearest enclosing scope that contains [- directly or indirectly -] both the using-directive and the nominated namespace. (7.3.4 [namespace.udir])

This means that both uint declarations appear at the global namespace scope when looked up after the using-directive in other.

A using-declaration, like any other declaration, declares a name at the scope in which it appears. This is why, in the second example, using mine::uint; hides the uint introduced by using namespace mine; as the latter appears to come from the global scope.


Your original code confuses the compiler, because the uint can be either

::uint

or

::mine::uint

therefore compiler throws that error message to you. In the "fix", the using mine::uint explicitly specified that ::mine::uint shall be preferred.

However, typedef conflict shall be avoided IMO. It makes the code so hard to maintain.


I can't cite chapter and verse for you, but this makes sense to me. If the compiler can't find the symbol uint in the current namespace, it looks to other namespaces to see if it can find the symbol there. Since it finds it in two other namespaces, it's ambiguous.

When you said using mine::uint you imported that symbol into the current block, so it's found before the other namespaces need to be checked.


It doesn't conceal the global one. That's why you have the ambiguity.

0

精彩评论

暂无评论...
验证码 换一张
取 消

关注公众号