命名空間
C#10 新功能====================
命名空間格式:聲明所有后續聲明都是已聲明的命名空間的成員:
//C#10 命名空間的新寫法,這種方式一個文件只能有一個命名空間。 //命名空間后面只能是類名、枚舉、結構 namespace MyNamespace; public class P { } public class Pr { }
也可以不行命名空間,這種方式編譯成dll時候,所有的內容會默認防止 類Program 的main函數里面。而Proram 沒有命名空間.
Proram 沒有命名空間,所有在寫反射時候,Program前面沒有命名空間。
Assembly se=Assembly.GetExecutingAssembly(); Type typ= se.GetType("Program", false);
//正常的類,前面應該加命名空間
Assembly se=Assembly.GetExecutingAssembly();
Type typ= se.GetType("NameSpace.Program", false);
全局的 using#
利用全局 using 可以給整個項目啟用 usings,不再需要每個文件都寫一份。比如你可以創建一個 Import.cs,然后里面寫:
using System; using i32 = System.Int32;
然后你整個項目都無需再 using System
,並且可以用 i32
了。
===============================
命名空間是一系列類型名稱的領域。通常情況下,類型組織在分層的命名空間里,既避免了命名沖突又更容易查找。例如,處理公鑰加密的RSA類型就定義在如下的命名空間下:
System.Security.Cryptography
命名空間組成了類型名的基本部分。下面代碼調用了RSA類型的Create方法:
System.Security.Cryptography.RSA rsa=System.Security.Cryptography.RSA.Create();
命名空間是獨立於程序集的。程序集是像.exe或者.dll一樣的部署單元。命名空間並不影響成員的public、internal、private的可見性。
namespace關鍵字為其中的類型定義了命名空間。例如:
namespace outer.Middle .Inner { class classl { } class Class2 { } }
命名空間中的“.”表明了嵌套命名空間的層次結構。下面的代碼在語義上和上一個例子是等價的:
namespace outer( namespace Middle{ namespace Inner{ class Classl {}class Class2 {}} })
類型可以用完全限定名稱(fully qualified name),也就是包含從外到內的所有命名空間的名稱,來指定。例如,上述例子中,可以使用Outer.Middle.Inner.Class1來指代Class1。
如果類型沒有在任何命名空間中定義,則它存在於全局命名空間(global namespace)中。全局命名空間也包含了頂級命名空間,就像前面例子中的Outer命名空間。
1、using指令
using指令用於導入命名空間。這是避免使用完全限定名稱來指代某種類型的快捷方法。以下例子導入了前一個例子的Outer.Middle.Inner命名空間:
using outer.Middle . Inner;class Test
{
static void Main ( ){
classl c;l/ Don't need fully qualified name}
}
在不同的命名空間定義相同名稱的類型是完全合法的,這也是命名空間存在的最基本的意義。然而,假設開發者同時導入了這些命名空間,在引用同名類型時會收到來自編譯器的錯誤,(這個問題可以用2.3.5小節的類型和命名空間別名解決)。
2、using static指令
從C#6開始,我們不僅可以導入命名空間還可以使用using static指令導入特定的類型。這樣就可以直接使用類型靜態成員而不需要指定類型的名稱了。在接下來的例子中,我們這樣調用Console類的靜態方法WriteLine:
using static system.Console;class Test
{
static void Main(){ writeLine ( "Hello");})
using static指令將類型的可訪問的靜態成員,包括字段、屬性以及嵌套類型(后續章節會講解),全部導入進來。同時,該指令也支持導入枚舉類型的成員(后續章節會講解)。因此如果導入了以下的枚舉類型:
using static System.Windows.Visibility;
我們就可以直接使用Hidden而不是Visibility.Hidden了:
var textBox = new TextBox { Visibility = Hidden }; // XAML- style
C#編譯器還沒有聰明到可以基於上下文來推斷出正確的類型,因此在導入多個靜態類型導致二義性時會發生編譯錯誤。
3、命名空間中的規則
3.1、名稱范圍
外層命名空間中聲明的名稱能夠直接在內層命名空間中使用。以下示例中的Class1在Inner中不需要限定名稱:
namespace outer{
class Classl { }
namespace Inner{
class Class2 : classl{ }}
)
使用統一命名空間分層結構中不同分支的類型需要使用部分限定名稱。在下面的例子中,SalesReport類繼承Common.ReportBase:
namespace MyTradingcompany{
namespace C ommon
class ReportBase { }}
namespace ManagementReporting{
class salesReport : Common. PeportBase{ }}
}
3.2、名稱隱藏
如果相同類型名稱同時出現在內層和外層命名空間中,則內層類型優先。如果要使用外層命名空間中的類型,必須使用它的完全限定名稱。
namespace outer
class Foo { }
namespace Inner{
class Foo { }
class Test{
Foo fl;
// - outer .Inner.Foo
outer.Foo f2;/l = outer.Foo
)
})
所有的類型名在編譯時都會轉換為完全限定名稱。中間語言(IL)代碼不包含非限定名稱和部分限定名稱。
3.3、重復的命名空間
只要命名空間內的類型名稱不沖突就可以重復聲明同一個命名空間:
namespace outer.Middle .Inner{
class Class1 {}}
namespace outer. Middle . Inner{
class class2 {}
上述例子也可以分為兩個不同的源文件,並將每一個類都編譯到不同的程序集中(這個用處很大)。
3.4、嵌套的using指令
我們能夠在命名空間中嵌套使用using指令,這樣可以控制using指令在命名空間聲明中的作用范圍。在以下例子中,Class1在一個命名空間中可見,但是在另一個命名空間中不可見:
name space N1{
class Classl { }}
namespace N2
{
using Nl;
class class2 : class1 { }
}
namespace N2
{
class Class3 : class1 {}l /compile-time error
}
3.5、類型和命名空間別名
導入命名空間可能導致類型名稱的沖突,因此可以只導入需要的特定類型而不是整個命名空間,並給它們創建別名。例如:
using PropertyInfo2 = system.Reflection.PropertyInfo;class Program{ PropertyInfo2 p; }
下面代碼為整個命名空間創建別名:
using R = system.Reflection;
class Program { R.PropertyInfo p; }