Пространство имен и класс с одинаковым именем?


Я организую проект библиотеки, и у меня есть центральный класс менеджера с именем Scenegraph и целая куча других классов, которые живут в пространстве сцены.

то, что я действительно хотел бы, чтобы scenegraph был MyLib.Scenegraph и другие классы MyLib.Scenegraph.*, но, похоже, единственный способ сделать это - сделать все остальные классы внутренними классами Scenegraph в Scenegraph.cs-файл, и это просто слишком громоздко.

вместо этого, я организовал его как Mylib.Scenegraph.Scenegraph и MyLib.Scenegraph.*, какой вид работ, но я нахожу, что Visual Studio запутывается при некоторых условиях относительно того, имею ли я в виду класс или пространство имен.

есть хороший способ организовать этот пакет, так что это удобно для пользователей без скачки все мои код в unmaintainable бардак?

5 65

5 ответов:

Я не рекомендую вам называть класс, как его пространство имен, см. этой.

в руководстве по проектированию каркаса говорится в разделе 3.4 "не используйте то же имя для пространства имен и тип в этом пространстве имен". То есть:

namespace MyContainers.List 
{ 
    public class List { … } 
}

почему это зло? О, позвольте мне считать способами.

вы можете попасть в ситуации, когда вы думаете, что вы имеете в виду для одной вещи, но на самом деле имеют в виду что-то еще. Предположим вам в конечном итоге в этой неудачной ситуации: вы пишете бла.DLL и импорт Фу.DLL и бар.DLL, которые, к сожалению, оба имеют тип называется фу:

// Foo.DLL: 
namespace Foo { public class Foo { } }

// Bar.DLL: 
namespace Bar { public class Foo { } }

// Blah.DLL: 
namespace Blah  
{   
using Foo;   
using Bar;   
class C { Foo foo; } 
}

компилятор выдает ошибку. " Foo " неоднозначно между Foo.Фу и Бар.Foo. облом. Я думаю, я исправлю это, полностью уточнив имя:

   class C { Foo.Foo foo; } 

Теперь это дает ошибку неоднозначности"Foo in Foo.Foo-это двусмысленно между Фу.Foo и Bar.Фу". Мы все еще не знаем к чему относится первый Foo, и пока мы не сможем это выяснить, мы даже не пытайтесь понять, к чему относится второй.

Я бы предложил вам следовать совету, который я получил на microsoft.public.dotnet.languages.csharp использовать MyLib.ScenegraphUtil.Scenegraph и MyLib.ScenegraphUtil.*.

предоставление того же имени пространству имен и классу может запутать компилятор, как говорили другие.

как назвать его тогда?

Если пространство имен имеет несколько классов, то найдите имя, которое определяет все эти классы.

Если пространство имен имеет только один класс (и отсюда соблазн дать ему то же самое имя) назовите пространство имен Имя_классаNS. Вот как Microsoft называет свои пространства имен по крайней мере.

CA1724: Type Names Should Not Match Namespaces ...

в принципе, если вы следуете анализу кода для правильного кодирования, это правило говорит не делать то, что вы пытаетесь сделать. Анализ кода - это очень полезным в помощи вам найти потенциал вопросы.

просто добавить мои 2 цента:

у меня есть следующий класс:

namespace Foo {
    public struct Bar {
    }
    public class Foo {
        //no method or member named "Bar"
    }
}

клиент был написан такой:

using Foo;

public class Blah {
    public void GetFoo( out Foo.Bar[] barArray ) {
    }
}

прощая ошибку GetFoo не возвращая вывод вместо использования параметра out, компилятор не смог разрешить тип данных Foo.Бар. ][ Он возвращал ошибку: не удалось найти тип или пространство имен Foo.Бар.

похоже, что при попытке компиляции он разрешил Foo как класс и не нашел встроенный класс бар в классе Foo. Он также не смог найти пространство имен Foo.Бар. Он не смог найти панель классов в пространстве имен Foo. Точки в пространстве имен не являются синтаксическими. Вся строка-это маркер, а не слова, разделенные точками.

это поведение было показано VS 2015 под управлением .Net 4.6