程序员人生 网站导航

C#学习日记29----二维索引器 与 foreach遍历索引器

栏目:php教程时间:2016-02-28 11:09:04

上1篇结尾的时候我留下了几个问题,由于要断电了没有解决,这1篇我们继续上1篇的内容。点这里回到上1篇

问题1:

数组有多维度的,索引器也能够是多维的吗???

索引器可以是多维的,上1篇中我们定义的索引器只是1维索引器,同数组1样可以定义多维索引器。比如我们索引电影院的1个放映室的坐位号,第1排第1列为1号,1排2列为2号……以下:

using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace Test1 {//定义cinema类包括1个2维数组与1个2维访问器 class cinema {//定义1个2维数组 private string[,] seat = new string[5, 5]; //定义1个2维访问器 public string this[uint a, uint b] { get { return seat[a, b]; } set { seat[a, b] = value; } } } class Program { static void Main(string[] args) { cinema movieroom = new cinema();//实例化 //for循环遍历写入 for (uint i = 1; i < 5; i++) { for (uint j = 1; j < 5; j++) { movieroom[i, j] = "第" + i + "排 第" + j + "列"; } } //for循环遍历读出 for (uint i = 1; i < 5; i++) { for (uint j = 1; j < 5; j++) { Console.WriteLine(movieroom[i,j]+" "+((i⑴)*4+j)+"号"); } } } } }


结果:


2维的索引器就是如此了,其他多维数的都以此类推,就不介绍了。


问题2:

数组能够使用foreach语句进行简单快捷的遍历,索引器也能使用foreach语句遍历么???

这个也是可以的,在解决这个问题的时候有必要弄清楚foreach的履行步骤与原理.

foreach语句:

C#中编译器会把foreach语句转化为IEnumerable接口的方法和属性,比如:

string[] str = new string[] { "HC1", "HC2", "HC3", "HC4" };//定义1个数组 foreach (string i in str)//使用foreach遍历 { Console.WriteLine(i); }


但是foreach语句会被解析为下面的代码段。

using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Collections; //注意添加这个命名空间,否则没有IEnumerator这个类 namespace Example { class Program { static void Main(string[] args) { string[] str = new string[] {"HC1","HC2","HC3","HC4" }; //定义1个数组 //调用GetEnumerator()方法,取得数组的1个枚举 IEnumerator per = str.GetEnumerator(); //在while循环中,只要MoveNext()返回true,就1直循环下去 while (per.MoveNext()) { //用Current属性访问数组中的元素 string p = (string)per.Current; Console.WriteLine(p); } } } }


结果都1样:


我们对string查看定义发现,string继承于IEnumerable接口,IEnumerable接口中只有1个方法GetEnumerator();(该方法已在string类中被实现了该方法的作用是,返回1个循环访问集合的枚举器IEnumerator,我们在转IEnumerator的定义,它也是1个接口,里面只有3个方法的声明,Current(获得集合中确当前元素),MoveNext(将枚举数推动到集合的下1个元素,成功返回true,超出结尾返回false),Reset( 将枚举数设置为其初始位置,该位置位于集合中第1个元素之前),也就是说,如果在我们自定义的类中没有实现GetEnumerator方法,和Current、MoveNext方法,就不能使用foreach语句遍历了。


foreach语句遍历自定义类:

还是上面电影院的例子,不过这次我们不用for循环输出,而是实现foreach语句遍历输出,以下:

using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Collections; //添加这个很有必要 namespace Test1 {//定义cinema继承IEnumerable接口实现GetEnumerator()功能 class cinema:IEnumerable {//定义1个2维数组 private string[,] seat = new string[5, 5]; //定义坐位号码 static public int index=⑴; //定义1个2维索引器 public string this[uint a, uint b] { get { return seat[a, b]; } set { seat[a, b] = value; }//set访问器自带value参数 } //实现GetEnumerator方法 public IEnumerator GetEnumerator() { return new ienumerator(seat); //利用构造方法传入seat参数 } //由于上面返回值的需要所以继承接口IEnumerator并实现方法 private class ienumerator:IEnumerator { private string[,] seats; //将传入的seat数组赋给它 public ienumerator(string[,] s) { seats = s; } //定义Current的只读属性 public object Current { //根据坐位号推算数组的坐标也就是物理位置 get { return seats[1+(index/4), (index%4)+1]; } } //定义向下移动的规则 public bool MoveNext() { index++; //索引下1个坐位号的位置 if (index <= 15) { return true; } else return false; } //由于这个程序中用不到这个方法所以不实现,但是必须得写上否则会报错 public void Reset() { } } } class Program { static void Main(string[] args) { cinema movieroom = new cinema();//实例化 //for循环索引写入 for (uint i = 1; i < 5; i++) { for (uint j = 1; j < 5; j++) { movieroom[i, j] = "第" + i + "排 第" + j + "列"; } } //调用foreach语句遍历输出 foreach (string i in movieroom) { Console.WriteLine(i+" "+(cinema.index+1)+"号"); } } } }


结果:

结果是1样的。。。。

版权声明:本文为博主原创文章,未经博主允许不得转载。

------分隔线----------------------------
------分隔线----------------------------

最新技术推荐