C#学习笔记

1.数组

Object myObjArr = new Object[5] {1, 2, 3, 4, 5};

Array.Copy(Arry1, Arry2, 3);

Array.Sort(Array myObjArr);

myObjArr.Length;

myObjArr.Rank;

myObjArr.GetLength(0);

myObjArr.GetUpperBound(0);

myObjArr.GetLowerBound(0);

 

2.在C#中,在一个字符串前面使用@符号,指明转义序列不被处理,字符串中间的空格和回车等符号,也都会输出。

3.可空修饰符

int? a = null;

 

4.注释

 5.查看编译选项

在Slolution Explorer中右击工程名,选择Properties,在打开的页面中选择Build即可。

6.字符串类型转换成对应的数值类型

string str = "9.11E-31";

float fa = float.Parse(str);

float fc = Convert.ToFloat(str);

bool ba = true;

string sa = ba.ToString();

7. TryParse()和Parse()的区别

            double number;
            string input;
            Console.Write("Enter a number: ");
            input = Console.ReadLine();
            if (double.TryParse(input, out number))
            {
                ;
            }
            else
            {
                Console.WriteLine("The text entered was not a valid numbler");
            }

TryParse()和Parse()的关键区别在于,假如转换失败,那么TryParse()不会引发异常。string到数值类型的转换往往取决于输入文本的用户。用户完全可能输入无法成功解析的数据。使用TryParse()而不是Parse(),就可以避免在这种情况下引发异常(我们已经预见到用户可能输入无效数据)。

8.分配数组,但不指定初始值

string[] languages = new string[9];

分配一个数组但不指定初始值仍然会初始化每个元素。“运行时”会将每个元素初始化为他们的默认值,如下所示:

  • 引用类型(比如string)初始化为null;
  • 数值类型初始化为零;
  • boo初始化为false;
  • char初始化为'\0'。

9.数组类的方法使用需要注意的地方:

  • 在使用BinarySearch()方法之前,有必要对数组进行排序。如果值不按升序进行排序,会返回不正确的索引。如果搜索元素不存在,那么返回的是负值。使用取反运算符~index,会返回大于搜素值的第一个索引(如果有的话)。
  • clear()方法不删除数组的元素,而且不将长度设为零,而是将数组中的每个元素都设为默认值(false、0或者null)。

 10.数组的复制

默认情况下,将一个数组变量赋值给另一个数组变量只会复制数组引用,而不是数组中单独的元素。要创建数组的一个全新副本,需使用数组的Clone()方法。该方法将返回数组的一个副本,更改这个新数组中的任何成员都不会影响原始数组的成员。

11.常见数组编码错误

12.数学常量

在System.Math类中,pi和E有着更精确的定义,因此,可以不必硬编码一个数学常量,而使用System.Math.PI或者System.Math.E。

13.在编译输出窗口内显示warning和error的个数

Tools->Option->Project and Solution->General    Always show Error List if build finishes with errors.

14.常见的命名空间

15.全局方法

C#没有提供全局方法支持,一切都必须出现在一个类定义中。这正是Main()方法被标记为static的原因:static在这里等价于C++的全局方法和Visual Basic的模块方法。

16.消除多个Main()方法的歧义

假如一个程序包含的两个类都有Main()方法,那么可以在命令行上指定具体是哪个类包含了程序的入口点。利用csc.exe的/m选项开关,可以指定包含Main()的那个类的完全限定类名。

17.方法的out参数

        static void Main(string[] args)
        {
            

            int a = 10;
            int b = 0;
            int c;
            c = GetInt(a, out b);
            Console.WriteLine(c);
            Console.WriteLine(b);
        }

        static int GetInt(int a, out int b)
        {
            b = a;

            return a;
        }

18.方法的可变参数,即参数数据

19.返回一个目录中所有.cs文件包含的代码行数

using System;
using System.IO;

public static class LineCounter
{
  static void Main(string[] args)
    {
                int totalLineCount = 0;
            string directory;
            if (args.Length > 0)
            {
                directory = args[0];
            }
            else
            {
                directory = Directory.GetCurrentDirectory();
            }

            totalLineCount = DirectoryCountLines(directory);
            Console.WriteLine(totalLineCount);
    }
        static int DirectoryCountLines(string directory)
        {
            int lineCount = 0;
            foreach (string file in Directory.GetFiles(directory, "*.cs"))
            {
                lineCount += CountLines(file);
            }

            foreach (string subDirectory in Directory.GetDirectories(directory))
            {
                lineCount += DirectoryCountLines(subDirectory);
            }

            return lineCount;
        }

        private static int CountLines(string file)
        {
            string line;
            int lineCount = 0;
            FileStream stream = new FileStream(file, FileMode.Open);
            StreamReader reader = new StreamReader(stream);
            line = reader.ReadLine();

            while (line != null)
            {
                if (line.Trim() != "")
                {
                    lineCount++;
                }
                line = reader.ReadLine();
            }

            reader.Close();
            return lineCount;
        }
}

 20.调用方法时,指定参数名

static void Main()
{
            DisplayGreeting(
                firstName:"Inigo", lastName:"Montoya");
}

        static void DisplayGreeting(
            string firstName,
            string middleName = default(string),
            string lastName = default(string))
        {
            ;
        }

 21.异常处理

虽然catch块的数量可以随意,但处理异常的顺序千万不要随意。catch块必须按照从最具体到最不具体排列。System.Exception数据类型是最不具体的,所以它应该最后出现。System.FormatException排在第一,因为它所处理的是最具体的异常。无论try块中的代码是否引发一个异常,finally块都会执行。

22.常见的异常类型

 23.编程特点

现如今,进行成功编程的关键在于能够提供恰当的组织和结构,以满足越来越大的应用程序的复杂需求。

24.构造器声明

开发者应该注意到既在声明中又在构造器内部进行赋值的情况。假如一个字段在声明时被赋值,那么只有在这个赋值发生之后,构造器内部的赋值才会发生。所以,最终生效的是构造器内部的赋值,它会覆盖声明时的任何赋值。因此,有必要考虑一种编码风格,避免在同一个类中,既在声明时赋值,又再构造器中赋值。

25.静态成员

和以前的许多语言不同,C#没有全局变量或全局函数的概念。C#中的所有字段和方法都出现在一个类的上下文中。在C#中,与全局字段或函数等价的是静态字段或方法。“全局变量或函数”和“C#的静态字段或方法”没有功能上的差异,只是静态字段或方法可以包含访问修饰符,比如private,从而对访问进行限制,并提供更好的封装性。

静态字段不是从属于实例,而是从属于类本身。因此,从类的外部访问静态字段时,需要使用类名。

26.静态类

在声明一个类时使用static关键字,具有两个方面的意义。首先,它防止程序员写代码来实例化Sample类。其次,它防止在类的内部声明任何实例字段或方法。既然类无法被实例化,实例成员也没有了意义。

静态类的另一个特征在于,C#编译器会自动在CIL代码中把它标记为abstract和sealed,这会将类指定为不可扩展,即不能从它派生出其他类。

27.扩展方法

扩展方法的要求如下:

  • 第一个参数是要扩展或者要操作的类型,这成为“被扩展的类型”;
  • 为了指定扩展方法,要在被扩展的类型名称前面附加this修饰符;
  • 要将方法作为一个扩展方法来访问,要用using指令导入扩展类型的命名空间,或者使扩展类型和调用代码在同一个命名空间中。

28.public常量应该是恒定值

public常量应该是恒定不变的。否则,如果对它进行了修改,那么在使用它的程序集中,不一定能反映出这个修改。如果一个程序集引用了另一个程序集中的常量,常量值将直接编译到引用程序集中。所以,如果被引用程序集中的值发生改变,而且引用程序集没有重新编译,那么引用程序集将继续使用原始值,而不是新值。将来可能改变的值应该制定为readonly,不要指定为常量。

29.readonly字段

 30.C#是单一继承

在C#中不允许一个类是多个类的派生类;

31.基类的重写

C#支持重写实例方法和属性,但是不支持重写字段或任何静态成员。

32.抽象类

抽象类是仅供派生的类。无法实例化一个抽象类,只能实例化从它派生的类。不抽象,可直接实例化的类成为具体类。

不可实例化只是抽象类的一个较次要的特征。其主要特征在于它包含抽象成员。抽象成员是不具有实现的一个方法或属性,其作用是强制所有派生类提供实现。

32.System.Object的成员

 33.接口和类的比较

 34.值类型

值类型需要的内存量会在编译时固定下来,而且不会在运行时改变。因为大小是固定的,所以值类型可以存储在成为栈(stack)的内存区域中。

引用类型指向的内存区成为堆(heap)。

除了了string和object,所有C#基本类型都是值类型,包括struct 。

35.避免拆箱

拆箱指令不包括将数据复制回栈的动作,但在C#中,只有当值类型作为引用类型的一个字段访问时才能直接访问堆上的值类型。由于接口是引用类型,所以在通过接口访问已装箱的值时,拆箱和复制可以避免。

当调用值类型的接口方法时,实例必须是一个变量,因为方法可能会改变这个值。由于拆箱会生成一个托管地址,运行时就会有一个存储位置和一个变量。因此,运行时只传递接口的托管地址,并不需要拆箱操作。

36.可访问性修饰符

37.生成XML文档

右击工程名称,选择Build标签,此标签页的下部有Output,勾上XML documentation file复选框即可。这样就可以将代码以XML格式书写的注释输出到指定的XML文件中。

再利用免费的GhostDoc和开源项目Ndoc可以轻松将地将XML文件生成文档。

38.异常处理的指导原则

  1. 只捕捉你能处理的异常;
  2. 不要隐藏(bury)你不能完全处理的异常;
  3. 尽可能少地使用System.Exception和常规catch块;
  4. 避免在调用栈较低的位置报告或记录异常;
  5. 在一个catch块中使用throw;而不是throw <异常对象>语句;

39.泛型

利用泛型,可以在声明变量时创建用来处理特定类型的特殊数据结构。

在方法中执行显式转型,相较于在泛型版本中执行隐式转型,前者能够更加明确地描述所发生的事情。开发者在泛型方法中执行转型时,假如没有约束来验证转型的有效性,那么一定要非常小心。

 参考文献:

[1] 《C#本质论》

posted @ 2013-07-04 17:31  朝雾之归乡  阅读(524)  评论(0编辑  收藏  举报