c#面向对象中static 关键字

c#面向对象中static 关键字

常用的的莫过于三大类:

静态类:类可以声明为 static 的,以指示它仅包含静态成员

 public static class StaticClass
    {
        //1.不能被实例化 ,也不能被继承 
       // 2.仅仅包含静态成员 string name = "";这样是行不通滴,方法也是这样滴,总之: 静态类中不包含非静态成员;
       // 3.
       // 
        /*
          静态类和私有构造构造函数的区别:
          1.私有构造函数依然可以从内部实例化对象,
           而静态类禁止从任何地方实例化类,其中包括从类自身内部
       
        */
    }

实例分析A:

    public class ClassA
    {
        public static string AppName = "hello, this is a static class test";
        public static int num = 5;

        public ClassA()
        {
            num = 15;
        }

        public static int getNum()
        {
            return num;
        }
    }

在主函数中调用ClassA的静态方法

        static void Main(string[] args)
        {
            int num=ClassA.getNum();
            Console.WriteLine(num);
            Console.ReadLine();
        }

最终的输出结果为:5

原因分析:

虽然有实例构造函数,但对classA类没有进行实例化,所以该实例构造函数没有被调用;

主函数代码修改如下:

        static void Main(string[] args)
        {
            ClassA a = new ClassA();
            int num=ClassA.getNum();
            Console.WriteLine(num);
            Console.ReadLine();
        }

输出结果为:15

如果类不声明为静态类(static class),很容易出现类似于上面的错误。修改为静态类

    public static class ClassA
    {
        public static string AppName = "hello, this is a static class test";
        public static int num = 5;

        static ClassA()
        {
            num = 15;
        }

        public static int getNum()
        {
            return num;
        }
    }

关于静态构造函数的补充:

(1) 静态构造函数不可继承;

(2) 静态构造函数可以用于静态类,也可用于非静态类;

(3) 静态构造函数无访问修饰符、无参数,只有一个 static 标志;

(4) 静态构造函数不可被直接调用,当创建类实例或引用任何静态成员之前,静态构造函数被自动执行,并且只执行一次。

 

实例分析B:如果是一个类中全部封装的是被外部调用的额方法,那么可以考虑将该类申明为static

 public class sqlHelp
    {
        public void do1()
        {
        }
        public void do2()
        {
        }
    }

    public static class sqlHelper
    {
        public static void do1()
        {


        }
        public static void do2()
        {

        }

    }

 
    class Program
    {
        static void Main(string[] args)
        {
      
            //调用去方法
            sqlHelp help = new sqlHelp();
            help.do1();
            sqlHelper.do1();
            //终结:类没有属性,全是方法,那么,有必要为了调用类中的方法,先实例化一个对象出来吗?
            //省略了构造一个对象的性能损耗,虽然可以忽略不计。其次,对程序员比较友好,调用类的方法更加的方便。

            
        }
    }

 

静态变量:

 

静态方法:

 

我们来看两道题!

第一题:

  class Program
    {
        public static int i = 0;

        public Program()
        {
            int i = 1;
            Console.WriteLine("实例构造函数方法被调用");
        }
        static Program()
        {
            i = 2;
            Console.WriteLine("静态构造函数被执行");
        }
        static void Main(string[] args)
        {

            Console.WriteLine(Program.i);

            Program p = new Program();
            Console.WriteLine(Program.i);

        }
    }
}

答案:i为2,首先,类被加载,所有的静态成员被创建在静态存储区,i=0;接着调用了类的成员,这个时候静态构造函数别调用 i=2。

        i为1,实例化后,调用构造函数,i=1,因为静态构造函数只执行一次,不能再被执行了。

第二题:

                             
 using System;
 
namespace teststatic
{
    class class1
    {
        static int i = getNum();
        int j = getNum();
 
        static int num = 1;
        
        static int getNum()
        {
            return num;
        }
 
        static void Main(string[] args)
        {
            Console.WriteLine("i={0}",i);
            Console.WriteLine("j={0}", new class1().j);
            Console.Read();
        }
    }
}     
                    

Console.WriteLine(string.Format("i={0}",i)); 这里i是static变量,而且类class1是第一次被引 用,要先为class1里面所有的static变量分配内存。

指令在逻辑还是一条一条的按顺序执行的,所以 先为static int i分配内存,并且在该内存中保持int的缺省值0,接着再为static int num 变量分配内存,

值当然也为0。

然后执行第二步,

为变量赋值:先为static int i变量赋值,i=getNum(),

看getNum里面的代码,就是return num,这个时候num的值是0,

于是i就为0了。然后对变量num赋值,num=1;这行代码执行后,

num就为1了。

所以最后的结果为:

 i=0 j=1

posted @ 2015-12-19 16:03  咕-咚  阅读(346)  评论(0)    收藏  举报