《隨筆四》——C#中的 “ 索引器和屬性的相同點和不同點、索引器與陣列的區別、索引器的過載 ”
目錄
關於索引器的詳細請看這裡《隨筆三》——C#中的“ 索引器” https://blog.csdn.net/qq_34536551/article/details/83926260
索引器(Indexer)
索引器允許類或結構的例項就像陣列一樣進行索引。索引器類似於屬性,不同之處在於它們的取值函式採用引數。索引器允許類或者結構的例項按照與陣列相同的方式進行索引取值,索引器與屬性類似,不同的是索引器的訪問是帶參的。
定義索引器的方式與定義屬性有些類似,其一般形式如下:
[修飾符] 索引器型別 this[索引值型別 index] { get{//獲得屬性的程式碼} set{ //設定屬性的程式碼} }
修飾符包括: public, protected, private, internal, new, virtual, sealed, override, abstract, extern.
索引器型別是表示將要存取的陣列或集合元素的型別。
索引值型別表示該索引器使用哪一型別的索引來存取陣列或集合元素,可以是整數,可以是字串;this表示操作本物件的陣列或集合成員,可以簡單把它理解成索引器的名字,因此索引器不能具有使用者定義的名稱。
索引器和屬性的相同點和不同點
相同點:
● 索引器是一組get 和 set 訪問器, 與屬性類類似。
● 索引器和屬性有很多相似的:
和屬性一樣,索引器不用分配記憶體來儲存。
索引器和屬性都主要被用來訪問其它資料成員, 它們與這些成員資料相關聯,並可以提供讀取和寫入。
和屬性一樣,索引器可以只有一個訪問器,也可以兩個都有。
和屬性一樣,實現get 和 set 訪問器的程式碼不必一定要關聯到某個欄位和 屬性。 這段程式碼可以做任何事情或者什麼都不做。 只要get訪問器返回某個指定型別的值既可。
不同點:
索引器以函式簽名方式 this 來標識,而屬性採用名稱來標識,名稱可以任意。
索引器可以過載,而屬性不能過載。
屬性既可以宣告為例項屬性,也可以宣告為靜態屬性,索引器永遠屬於例項成員,因此不能宣告為static。
屬性有簡潔的自動實現屬性,而索引必須宣告完整。
索引器中引數列表中“ [ ]”必須至少宣告一個引數。
索引器可以有多個形參,例如當訪問二維陣列時。
屬性通常操作一個數據成員。索引器通常可以操作多個數據成員。
說明: 我們可以認為索引器是為類的多個數據成員提供get 和 set 的屬性,通過索引器,我們可以操作許多可能的資料成員。 那麼索引器本身可以是任何型別,不僅僅是數值型別。
索引器與陣列的區別
索引器的索引值(Index)型別不限定為整數:
用來訪問陣列的索引值(Index)一定為整數,而索引器的索引值型別可以定義為其他型別。
索引器允許過載
一個類不限定為只能定義一個索引器,只要索引器的函式簽名不同,就可以定義多個索引器,可以過載它的功能。
索引器不是一個變數
索引器沒有直接定義資料儲存的地方,而陣列有。索引器具有get和set訪問器。
索引器的過載
● 只要索引器的引數列表不同, 類就可以有人任意多個索引器。 僅僅是索引器型別不同是不行的。 這稱為索引器過載。
namespace Ch05Ex03
{
//定義一個能被索引的類
class Classes
{//對類的索引實質是對類中陣列的索引
public string[] StudentName = new string[6];
//定義索引器
public string this[int ID]
{
get
{
if (ID < 6)
{
return StudentName[ID];
}
return null;
}
set
{//set訪問器自帶value引數
if (ID < 6)
{
StudentName[ID] = value;
}
}
}
//過載索引器引數設為string型別
public uint this[string name]
{
get
{ //找到與name匹配的學號
uint index = 1;
while (StudentName[index] != name && index < 6)
{ index++; }
return index;
}
set { }
}
}
class Program
{
static void Main(string[] args)
{
Classes class4 = new Classes();
//索引寫入
for (int i = 1; i < 6; i++)
{
class4[i] = "HC" + i;
}
//索引讀出,通過學號索引出姓名
for (int j = 1; j < 6; j++)
{
WriteLine(j + "號\t" + class4[j]);
}
//通過姓名索引出學號
for (int k = 1; k < 6; k++)
{
string name = "HC" + k;
Console.WriteLine(name + "\t" + class4[name] + "號");//對比上面用法一樣引數不一樣
}
ReadKey();
}
}
}
輸出結果為:
1號 HC1
2號 HC2
3號 HC3
4號 HC4
5號 HC5
HC1 1號
HC2 2號
HC3 3號
HC4 4號
HC5 5號