Java或C#中的命名空间污染是否存在(如在C++中)?

mat*_*aly 16 c# c++ java namespaces

我一直对Java和C#如何处理命名空间的概念感到困惑.

首先,一些编程语言中命名空间污染的例子:

  1. using namespace std 对于C++.

    业内人士对此表示不满,但在开始编程时,初学者仍然被教导要这样做.这是一个关于处理全局命名空间的建议的问题

  2. import math.* 在Python中

在使用Python类时,我被告知不建议这样做,因为它污染了命名空间,并且首先允许访问数学库中的所有方法,Math.functionname但在编写具有重复名称的方法时可能会导致冲突.它显然导致了解释器的更多工作,因为它导入了所有函数,甚至那些未使用的函数.

  1. Ocaml中的open模块在顶层或ML文件中执行此操作可能会导致命名冲突.特别是如果写一个图书馆.

  2. JavaScript命名空间污染

问题:

在C#和Java中是否存在"命名空间污染"(即导入大量可能在编写方法时引发冲突的方法)(它们在很多方面类似)?为什么不?

当然,相关问题过于相似而无法提出另一个问题:

- 这是因为我们可能需要明确的@Override事情或某种预防措施?

- 它存在,但它不是一个东西,因为它不会像'使用命名空间std'那样造成太大的破坏,而且我不知道它对于学术课程中的软件开发是否相对较新?

我发现自己using在C#中有很多库,以避免为变量重命名命名空间,比如XElement

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
//the ones above are auto-generated by Visual Studio, too

using System.Xml.Linq;
Run Code Online (Sandbox Code Playgroud)

我会避免System.Xml.Linq.XElement每次创建XElement时都要做.就像我们std::cout在C++中总是要做的一样

或者在我常见的Java中:import java.util.linkedlist甚至import java.util.*

如果我的课程在别处使用,这些会不会导致命名空间污染?或者是因为它们只会"污染"特定的类范围而不是其他可能导入或继承我的类的类?

我试着寻找答案,但找不到一个,但我可能会错误地搜索搜索.

编辑4/20/2015:

正如@RealSkeptic所提到的,事实证明也不鼓励Java通配符导入.资源

除了下面接受的答案和答案之外,Java和C#中的导入本身也包含在内,因此即使有人使用通配符类型的导入将未使用的方法名称添加到命名空间,它也不会影响其他类.在类级别上,如果名称中发生冲突,Java和C#编译器将引发错误,引用模糊的导入,并且在问题解决之前无法进一步编译(例如通过重命名函数).

Mar*_*o13 4

正如其他人已经指出的,命名空间污染问题在 Java 中并不像在 C++ 中那么突出。名称空间污染是 C++ 中的一个问题(因此首先称为“污染”)的主要原因是它可能会导致其他模块中的错误。为什么\xe2\x80\x9cusing 命名空间 std;\xe2\x80\x9d 被认为是不好的做法?

\n\n

(这里令人担忧的是,这可能不仅仅指编译错误:对于编译错误,您被迫做一些事情并解决歧义。真正令人担忧的是,它可能会导致代码仍然可以正确编译,但之后只是调用了错误的函数!)

\n\n
\n\n

在 Java 中,每个import仅影响包含它的文件。这意味着上述污染仍可能在一档局部发生。(可以说:这只是作者的问题,才真正造成了命名空间污染,这也是公平的)

\n\n

与上述链接中的情况类似:假设您正在使用两个库,“ foo ”和“ bar ”。出于懒惰(或缺乏最佳实践的知识),您正在使用通配符导入:

\n\n
import foo.*:\nimport bar.*:\n\nclass MyClass {\n    void someMethod() {\n\n        // Assume that this class is from the "foo" librariy, and the\n        // fully qualified name of this class is "foo.Example"\n        Example e = new Example();\n    }\n}\n
Run Code Online (Sandbox Code Playgroud)\n\n

现在想象一下您升级了“ bar ”库的版本。新版本包含一个名为 的类bar.Example。那么上面的代码将无法编译,因为对该类的引用Example不明确。

\n\n

顺便说一句,同样的问题也可能出现在静态导入中。它更加微妙和微妙,碰撞的可能性也更大。这就是为什么他们说您应该非常谨慎地使用静态导入。

\n\n
\n\n

附注:当然,这些冲突和歧义很容易解决。您始终可以使用完全限定名称。大多数现代 Java IDE 都提供组织/优化导入的功能。例如,在 Eclipse 中,您始终可以按CTRL+ Shift+ ,这将(取决于Preferences->Java->Code Style->Organize ImportsO中的设置)将所有通配符导入替换为单个通配符导入。

\n