C# 变量和参数

        //栈--存储局部变量和参数的内存块。
        //逻辑上,栈会在函数进入和退出时增加或减少。
        static int Factorial(int x) //每一次进入这个方法的时候,就在栈上分配一个新的int,而每一次离开这个方法,就会释放一个int。
        {
            if (x == 0) return 1;
            return x * Factorial(x - 1);
        }

        static void Main(string[] args)
        {
            //堆--保存对象(例如引用类型的实例)的内存块。
            //新创建的对象会分配在堆上并返回其引用。
            //程序执行过程中,堆就被新创建的对象不断填充。.NET运行时的垃圾回收器会定期从堆上释放对象。
            StringBuilder ref1=new StringBuilder("obj1");
            Console.WriteLine(ref1);    //ref1在后续没有使用的情况下可立即被垃圾回收器释放

            StringBuilder ref2 = new StringBuilder("obj2");
            StringBuilder ref3 = ref2;  //此处将ref2的引用复制给ref3,虽然ref2之后不再使用,但是由于ref3保持着同一个StringBuilder对象的引用,因此在ref3使用完毕前它不会被垃圾回收器回收
            Console.WriteLine(ref3);
            //值类型的实例(和对象的引用)就存储在变量声明的地方。
            //如果声明为类的字段或数组的元素,则该实例会存储在堆上。
            //静态字段也会存储在堆上。与分配在堆上的对象(可以被垃圾回收)不同,这些变量一直存活直至应用程序域结束。


            //明确赋值:
            //局部变量在读取之前必须赋值
            //使用方法时必须提供函数的实际参数
            //运行时将自动初始化其他变量(例如字段和数组元素)。

            //以下示例将产生编译时错误
            //int x;
            //Console.WriteLine(x);   //使用了未赋值的局部变量x

            //字段和数组元素会自动初始化为其类型的默认值。
            int[] a = new int[3];
            Console.WriteLine(a[1]);    //0


            //默认值
            //所有类型的实例都有默认值。
            //预定义的默认值是按位取0的内存表示的值。

            //default关键字可用于获得任意类型的默认值。
            decimal b=default (decimal);
            Console.WriteLine(b);   //0


            //参数
            //使用ref和out修饰符可以控制参数的传递方式


            //按值传递参数(默认情况)
            int c = 8;
            Foo1(c);    //传入的是c的副本
            Console.WriteLine(c);   //c仍等于8

            StringBuilder d = new StringBuilder();
            Foo2(d);    //传入的是引用d的副本,Foo2方法将传入的参数赋值为null,并不会把d也赋值为null
            Console.WriteLine(d.ToString());    //test
            

            //ref修饰符
            //按引用传递参数
            int e = 8;
            Foo3(ref e);
            Console.WriteLine(e);   //9

            string f = "apple";
            string g = "banana";
            Swap(ref f, ref g);
            Console.WriteLine(f);   //banana
            Console.WriteLine(g);   //apple


            //out修饰符
            //与ref参数一样,out参数按引用传递
            string h, i;
            Split("abc def ghi",out h,out i);
            Console.WriteLine(h);   //abc def
            Console.WriteLine(i);   //ghi

            //从C# 7开始,允许在调用含有out参数的方法时直接声明变量
            Split("abc def ghi", out string j, out string k);
            Console.WriteLine(j);
            Console.WriteLine(k);

            //使用out参数的方法时,可使用下划线来丢弃那些不感兴趣的参数
            Split("abc def ghi",out string l, out _);   //丢弃第二个out参数


            //params修饰符
            //params参数修饰符只能修饰方法中的最后一个参数,它能够使方法接受任意数量的指定类型参数。
            //参数类型必须声明为数组
            int total = Sum(1, 2, 3, 4);
            Console.WriteLine(total);   //10
            //也可将普通的数组提供给params参数
            int total2 = Sum(new int[] { 1, 2, 3, 4 });
            Console.WriteLine(total2);  //10


            //可选参数
            Foo4(); //20


            //命名参数
            Foo5(x: 1, y: 2);   //1,2
            //也可以写作
            Foo5(y: 2, x: 1);   //1,2


            //var隐式类型局部变量
            //如果编译器能够从初始化表达式中推断出变量的类型,就能够使用var关键字来代替类型声明
            var m= "hello";    //string
            var n= 8;   //int

        }

        static void Foo1(int p)
        {
            p = p + 1;
            Console.WriteLine(p);
        }

        static void Foo2(StringBuilder p)
        {
            p.Append("test");
            p = null;
        }
        static void Foo3(ref int p)
        {
            p = p + 1;
            Console.WriteLine(p);
        }
        static void Swap(ref string a,ref string b)
        {
            string temp = a;
            a = b;
            b = temp;
        }
        static void Split(string name,out string firstName,out string lastName)
        {
            int i = name.LastIndexOf(' ');
            firstName = name.Substring(0,i);
            lastName=name.Substring(i+1);
        }
        static int Sum(params int[] ints)
        {
            int sum = 0;
            for (int i = 0; i < ints.Length; i++)
                sum += ints[i];
            return sum;
        }
        static void Foo4(int x = 20)
        {
            Console.WriteLine(x);
        }
        static void Foo5(int x,int y)
        {
            Console.WriteLine(x + "," + y);
        }
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容