【问题标题】:Comparing and Contrasting C++ vs C# namespace hierarchies比较和对比 C++ 与 C# 命名空间层次结构
【发布时间】:2015-02-15 08:06:43
【问题描述】:

我知道 C# 支持命名空间嵌套,就像 C++ 一样,它们都允许看起来像这样的代码...

namespace A {
    namespace B {
        ...
    }
}

来自 C++ 背景并潜入 C# 世界,我一直在沉思通过所有使用 .NET 必须发出的指令来显示组件的分层嵌套,例如

using System.Collections;
using System.Collections.Generic;

我确信 Microsoft 打算并将这些库设计为在逻辑上按层次组织,但如果没有查看源代码的帮助,我无法验证 System.Collections.Generic 是否具有 Generic 作为 Collections 的嵌套命名空间,但我认为它是,并且它是通过命名空间嵌套来完成的,就像在 A 和 B 中看到的那样。现在,一旦我开始在自己的源代码中编写东西并声明看起来像这样的代码

namespace C.D {
    ...
}

相对于层次结构,我在这里实现了什么?我是否在代码中引入了一个单一的命名空间标识符“C.D”,其中“。”只是一种友好的方式来建议可能存在或可能不存在的层次结构,具体取决于代码结构,还是我隐含地声明了两个命名空间“C”和“D”,其中 D 嵌套在 C 中?我在为我们的 C# 代码库编写 DevelopmentApplications 命名空间时遇到了这个问题,该命名空间旨在严格包含用于增强我们的软件以帮助其开发的所有开发工具。在这些工具中,我从未声明过独立的封闭命名空间 DevelopmentApplications(这是我在 C++ 中必须要做的事情)...

namespace DevelopmentApplications
{
   ...
}

...但总是创建类似的应用程序

namespace DevelopmentApplications.MyDevelopmentApp
{
   ...
}

我知道这个领域会引起一些人的困惑,因为以下question 作者正在努力理解 Foo.Bar.Baz 和 Foo.Bar 之间的关系。还有一个 C# 开发人员进入 C++ 领域的逆向 question 提供了对该问题的一些见解。

我想另一种表述问题的方式是,在 C++ 中,使用 '::' 运算符来完全限定我知道的类型可以保证声明该类型的代码嵌套在某个命名空间层次结构的深处。但在 C# 中使用 '.'运算符要完全限定某些类型,该类型是否还必须存在于某些深度嵌套的命名空间层次结构中?我在这里假设 C# 使用像 A.B.C 这样的命名空间不一定需要 A B 和 C 之间的层次关系,或者 A B 或 C 甚至作为单独的命名空间存在。

如果有人能找到或知道有关此语法的相关语言规范,我很乐意阅读。

【问题讨论】:

标签: c# c++ namespaces hierarchy layer


【解决方案1】:

C# 4.0 规范的第 9.2 节指出:

namespace-declarationqualified-identifier 可以是 单个标识符或由“.”分隔的标识符序列 令牌。后一种形式允许程序定义嵌套的命名空间 无需在词法上嵌套多个命名空间声明。例如,
namespace N1.N2
{
  class A {}
  class B {}
}

在语义上等价于

namespace N1
{
  namespace N2
  {
      class A {}
      class B {}
  }
}

你说:

我在这里假设 C# 使用像 A.B.C 这样的命名空间并不一定需要 A B 和 C 之间的层次关系,或者 A B 或 C 甚至作为单独的命名空间存在。

这个假设是错误的。命名空间A.B.C必然涉及全局命名空间中的命名空间A,命名空间A中的命名空间B,命名空间B中的命名空间C

【讨论】:

  • 很好的例子来表明两个命名空间声明的等价性。因此,该语法确实隐含地导致了 A 的存在,并且它对全局命名空间也是如此。我将编辑关于“单一名称空间标识符”的问题部分,以全局名称空间的形式进行说明。我实际上找到了说明您声明的规范的确切部分,9.2 命名空间声明
  • 该部分值得在这里公开:命名空间声明的限定标识符可以是单个标识符,也可以是由“.”分隔的标识符序列。令牌。后一种形式允许程序定义一个嵌套的命名空间,而无需在词法上嵌套多个命名空间声明。关于“没有词法嵌套多个命名空间声明”的那部分确实使我对 Adam Naylor 的问题和他对 C++ 中嵌套命名空间的词法痛苦的观察非常感兴趣,并且让我更加欣赏 C#!
  • @jxramos 确定;我已经编辑了帖子以包含该引用,并且我只是使用它作为示例,因为我们做了那么多。
  • 这是上面的restatement,它可能最接近需要在 C# 中解释这些复合命名空间声明的具有 C++ 思维方式的人。是简写! 8.12 命名空间和程序集命名空间可以嵌套,声明“namespace CSharp.Introduction {…}”是两级命名空间嵌套“namespace CSharp { namespace Introduction {…} }”的简写
【解决方案2】:

C#中的一些facts about namespaces

  1. 他们是集体的。您可以在几个不同的源文件中声明一个命名空间,编译器会将它们都视为同一个命名空间。

  2. 您可以将命名空间相互嵌套,但更常见的是在另一个源文件中简单地声明嵌套命名空间。

  3. 有一个global namespace,每个班级都可以通过global::访问

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2011-01-07
    • 2023-03-09
    • 2018-03-18
    • 1970-01-01
    • 1970-01-01
    • 2021-04-02
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多