博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
<NET CLR via c# 第4版>笔记 第16章 数组
阅读量:5093 次
发布时间:2019-06-13

本文共 3915 字,大约阅读时间需要 13 分钟。

//创建一个一维数组        int[] myIntegers;           //声明一个数组引用        myIntegers = new int[100];  //创建含有100个int的数组        //创建一个二维数组        double[,] myDoubles = new double[10, 20];        //创建一个三维数组        string[,,] myStrings = new string[5, 3, 10];        //创建交错数组        Point[][] myPolygons = new Point[3][];        myPolygons[0] = new Point[10];        myPolygons[1] = new Point[20];        myPolygons[2] = new Point[30];
  • 0基一维数组的性能是最佳的.因为可以使用一些特殊的IL指令.

16.1 初始化数组元素

// 1) 利用c#的隐式类型的局部变量功能:    var names1 = new string[] { "Alidan", "Grant" };    // 2) 利用C#的隐式类型的局部变量和隐式类型的数组功能:    var names2 = new[] { "Alidan", "Grant", null };    // 3) 额外的语法奖励(这里不能用var)    string[] names3 = { "Alidan", "Grant" };    // 4) 使用C#的隐式类型的局部变量\隐式类型的数组和匿名类型功能:    var kids = new[] { new { Name = "Aidan" }, new { Name = "Grant" } };    foreach (var kid in kids)        Console.WriteLine(kid.Name);

16.2 数组转型

  • 元素为引用类型的数组,如果维数相同,且元素源类型到目标类型存在隐式或显式转换,CLR 允许将数组元素从一种类型转型另一种.
  • CLR不允许将值类型元素的数组转型为其他任何类型,不过可用 Array.Copy 方法来模拟.
//创建二维 FileStream 数组    FileStream[,] fs2dim = new FileStream[5, 10];    //隐式转型为二维 Object 数组    object[,] o2dim = fs2dim;    //显示转型为二维 Stream 数组    Stream[,] s2dim = (Stream[,])o2dim;    //创建一维 Int32 数组(元素是值类型)    int[] ildim = new int[5];    //下面的代码创建元素为引用类型的数组,    //每个元素都是对已装箱 Int32 的引用    object[] obldim = new object[ildim.Length];    Array.Copy(ildim, obldim, ildim.Length);
  • 使用数组转型有性能损失,对数组元素赋值时,CLR必须在运行时检查数组包含元素的类型是否与新元素类型相符.
  • System.Buffer.BlockCopy() 方法比 Array.Copy() 方法快,但前者只支持基元类型,不提供像 Array 的 Copy 方法那样的转型能力.
  • Array.ConstrainedCopy 方法要么完成复制,要么抛出异常,总之不会破坏目标数组中的数据.

16.3 所有数组都隐式派生自 System.Array

16.4 所有数组都隐式实现 IEnumerable, ICollection 和 IList

  • System.Array 实现了 IEnumerable,ICollectionIList 三个接口,但未实现其对应的泛型接口.
  • CLR 创建一维 0 基数组类型时,CLR 自动使数组类型实现 IEnumerable<T>,ICollection<T>IList<T>(T是数组元素的类型) 接口.同时,还为数组类型的所有基类型实现这三个泛型接口,只要它们是引用类型(数组元素为值类型的,不为数组的基类型实现接口).

16.5 数组的传递和返回

  • 数组作为实参传给方法时,实际传递的是对该数组的引用.因此,被调用的方法能修改数组中的元素.
  • 方法返回数组对象时,如果元素数量为 0 ,强烈建议返回一个空数组,而不是 null ,因为调用方法时可以省去 null 检查.

16.6 创建下限非零的数组

16.7 数组的内部工作原理

  • 访问一维 0 基数组的元素比访问非 0 基一维或多维数组的元素稍快.因为:
    1. 有一些特殊 IL 指令处理一维 0 基数组,导致 JIT 编译器生成优化代码;
    2. For 循环时,JIT 编译器会将对 Length 属性的调用结果缓存起来,每次迭代检查的都是这个临时变量.(不要自作聪明自己缓存 Length 结果)
  • 如要提升性能,可以用交错数组代替矩形数组.
  • 矩形数组的访问方式 a[x,y] ,交错数组的访问方式 a[x][y]

16.8 不安全的数组访问和固定大小的数组

static class Program    {        static void Main(string[] args)        {            StackallocDemo();            InlineArrayDemo();        }        private static void StackallocDemo()        {            unsafe            {                const int width = 20;                char* pc = stackalloc char[width]; //在栈上分配数组                string s = "Jeffrey Richter"; //15个字符                for (int index = 0; index < width; index++)                {                    pc[width - index - 1] = (index < s.Length) ? s[index] : '.';                }                //下面这行代码显示".....rethciR yerffeJ"                Console.WriteLine(new String(pc, 0, width));            }        }        private static void InlineArrayDemo()        {            unsafe            {                CharArray ca;   //在栈上分配数组                int widthInBytes = sizeof(CharArray);                int width = widthInBytes / 2; //Char类型占2个字节                string s = "Jeffrey Richter"; //15个字符                for (int index = 0; index < width; index++)                {                    ca.Characters[width - index - 1] = (index < s.Length) ? s[index] : '.';                }                //下面这行代码显示".....rethciR yerffeJ"                Console.WriteLine(new String(ca.Characters, 0, width));            }        }    }    internal unsafe struct CharArray    {        //这个数组内联(嵌入)到结构中        public fixed char Characters[20];    }

在结构中嵌入数组,需满足:

  • 类型必须是结构(值类型);不能在类(引用类型)中嵌入数组.
  • 字段或其定义结构必须用 unsafe 关键字标记.
  • 数组字段必须用 fixed 关键字标记
  • 数组必须是一维 0 基数组.
  • 数组的元素类型必须是以下类型之一:Boolean,Char,SByte,Byte,Int16,Int32,UInt16,UInt32,Int64,UInt64,Single,Double

转载于:https://www.cnblogs.com/harry-wang/p/7345803.html

你可能感兴趣的文章
Aizu - 1378 Secret of Chocolate Poles (DP)
查看>>
csv HTTP简单表服务器
查看>>
OO设计的接口分隔原则
查看>>
数据库连接字符串大全 (转载)
查看>>
java类加载和对象初始化
查看>>
对于负载均衡的理解
查看>>
window.event在IE和Firefox的异同
查看>>
IO流写出到本地 D盘demoIO.txt 文本中
查看>>
Screening technology proved cost effective deal
查看>>
【POJ2699】The Maximum Number of Strong Kings(网络流)
查看>>
spring boot配置跨域
查看>>
BZOJ 1996 合唱队(DP)
查看>>
进击吧!阶乘——大数乘法
查看>>
安卓学习资料推荐-25
查看>>
Mysql数据库备份和还原常用的命令
查看>>
经典入门_排序
查看>>
Redis Cluster高可用集群在线迁移操作记录【转】
查看>>
二、spring中装配bean
查看>>
VIM工具
查看>>
javascript闭包
查看>>