菜鸟的问题
好记性不如烂笔头~。~

(https://www.runoob.com/csharp/csharp-delegate.html)

1.变量的生命周期与类的实例同步:当方法体执行完毕后,变量随之销毁。

2.常量:①静态常量:const;②动态常量:static readonly(转载博客:https://www.cnblogs.com/yanglang/p/9003770.html)

-1.const:编译时常量,程序在编译时将对常量值进行解析,并将所有的常量引用替换为相应的值;const默认为静态类型,所以在使用中不再使用static来修饰,否则导致编译报错;必须在声明的同时进行初始化(赋值);const常量只能赋予数字(整数、浮点数)、字符串以及枚举类型;

//错误常量声明
public const DateTime t = DateTime.MaxValue;

//使用readonly修改即可
public static readonly DateTime t = DateTime.MaxValue;

-2.(static) readonly:运行时常量,程序运行是进行赋值,赋值完成后便无法更改(只读变量);readonly常量只能声明为类字段,支持实例类型或静态类型,可以在声明的同时初始化或者在构造函数中进行初始化,初始化完成后便无法更改;

-3.可维护性:readonly常量是以引用的方式进行存储工作,莫个常量的值更新后,所有引用了改常量的地方均全部进行更新;const常量由于在声明是就进行了初始化,所以相对用于声明一些不会变动的值(比如一天=24小时),并且const在程序集中夸集使用时,当编译更新其中一个程序集时,另外的程序集不会同步更新

3.refout关键字:按地址传递,使用后都将改变原来参数的数值;ref与out在一定程度上解决了C#中的函数只能有一个返回值的问题

① ref:方法定义使用ref关键字时,调用对应的方法也必须带ref返回;

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace ConsoleApplication1
{
    class Program
    {
        static void Main(string[] args)
        {
            //初始化
            int a = 1;
            int b = 6;
            // 调用时带ref关键字,返回多个值
            RefFun(ref a,ref b);
            Console.WriteLine("a:{0},b:{1}", a, b);//输出:7和6说明传入Fun方法是a和b的引用
        }
       //使用ref定义方法
        static void RefFun(ref int a, ref int b) {
            a = a+b; 
            b = 6;
        }
    }
}
View Code

②.使用泛型来使用ref关键字交换两个整数

using System;

namespace IEnumerable
{
    class Program
    {
        static void Main(string[] args)
        {

            int a = 10;
            int b = 20;
            Console.WriteLine("ListNum one:{0},{1}",a, b);

            //交换两个整型数据
            ListNum<int>(ref a, ref b);
            Console.WriteLine("ListNum two:{0},{1}",a, b);
            Console.ReadKey();
        }

        //泛型方法
        public static void ListNum<T>(ref T a, ref T b)
        {
            T t;
            t = a;
            a = b;
            b = t;
        }


    }
}
View Code

-1.ref:有进有出

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Example_1
{
    class Program
    {
        static void Main(string[] args)
        {
            int a = 1;
            int b = 2;
            Console.WriteLine("交换前:a:{0},a:{1}",a,b);
            //调用RefFun进行赋值替换
            RefFun(ref a, ref b); 
            Console.WriteLine("交换后:a:{0},b:{1}",a,b);
            Console.ReadKey();
        }

       
        public static void RefFun(ref int a, ref int b)
        {
            int temp = a;
            a = b;
            b = temp;
            Console.WriteLine("RefFun方法体中:a:{0},b:{1}",a,b);
            
        }
    }
}
View Code

-2.ref参数再传入之前必须先初始化(赋值)

using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace IEnumerable
{
    class Program
    {
        static void Main(string[] args)
        {
            int b = 5;
            Console.WriteLine($"输出b:{b}");

            Num(ref b); //调用Num(ref b)函数前,必须给传递的参数b赋值
            Console.WriteLine($"输出ref的b:{b}");

            Console.ReadKey();
        }

        public static void Num(ref int a)
        {
            a *= 2;
        }
    }
}
View Code

② out:方法定义使用out关键字时,调用对应的方法也必须带out返回

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Example_1
{
    class Program
    {
        static void Main(string[] args)
        {
 
            int a =100;
            int b =20;
            OutFun(out a, out b);
            //附带奔方法体内的初始化的值进行输出
            Console.WriteLine("a:{0},b:{1}",a,b);
            Console.ReadKey();
        }


        public static void OutFun(out int a, out int b)
        {
            // 初始化
            int n = 3;
            int m = 5;
            a = n*m ;
            b = 1;
        }
    }
}
View Code

-1.out只出不进

-2.out参数不需要事先进行初始化,只要在传入前声明变量即可

using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace IEnumerable
{
    class Program
    {
        static void Main(string[] args)
        {
            int[] list = {1,2,3,4,5,6,7,8 };
            int d;

            // 调用代码可以把已赋值的变量用做out参数,但存储在该变量中的值会在函数执行时丢失
            Console.WriteLine($"out输出:{MaxList(list,out d)}");

            Console.WriteLine(d);

            Console.ReadKey();

        }

        static int MaxList(int[] ArrayList, out int v)
        {
            int a = ArrayList[0];
            v = 0;
            for (int i = 1; i < ArrayList.Length; i++)
            {
                if (ArrayList[i] > a)
                {
                    a = ArrayList[i];
                    v = i;
                }

            }
            return a;
        }
    }
}
View Code

③Example:

-1.Person.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Example_2
{
    public class Person
    {
        public string Name { get; set; }
        public int Age { get; set; }
    }
}
View Code

-2.Program.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Example_2
{
    class Program
    {
        static void Main(string[] args)
        {
            Person p = new Person { Name = "John", Age = 17 };
            //调用test前
            Console.WriteLine("前:姓名:{0}, 年龄:{1}",p.Name,p.Age);
            //传入 重新初始化的值
            Test(p);
            Console.WriteLine("后:姓名:{0}, 年龄:{1}", p.Name, p.Age);

            //小括号表示要是类的构造函数带有参数的话,必须传参小括号就不可省略
            Person ps = new Person (){ Name = "xx", Age = 1 };
            Person px = new Person { Name = "tt", Age = 2 };

            Test2(ps);
            Console.WriteLine("test2:姓名:{0}, 年龄:{1}",ps.Name,ps.Age);


            //REF与OUT
            Person p4 = new Person() { Name="yzz",Age=18};
            //调用ref
            Console.WriteLine("ref前:姓名:{0},年龄:{1}",p4.Name,p4.Age);
            Test3(ref p4);
            Console.WriteLine("ref后:姓名:{0},年龄:{1}",p4.Name,p4.Age);


           //out
            Person p5 = new Person(){ Name = "jio", Age = 20 };
            Console.WriteLine("OUT前:姓名:{0}, 年龄:{1}",p5.Name,p5.Age);
            Test4(out p5);
            if (p5!=null)
            {
                Console.WriteLine("out:姓名:{0},年龄:{1}",p5.Name,p5.Age);
            }
            Console.ReadKey();

        }

        /// <summary>
        /// 引用Person类
        /// </summary>
        /// <param name="p"></param>
        static void Test(Person p)
        {
            p.Name = "tom";
            p.Age = 12;
        }

        static void Test2(Person p)
        {
            p = new Person { Name = "Chen", Age = 20 };
        }

        static void Test3(ref Person p)
        {
            p = new Person();
            p.Name = "Boy";
            p.Age = 13;
        }

        static void Test4(out Person p)
        {
            p = new Person();
            p.Name = "YY";
            p.Age = 17;
        }
    }
}
View Code

4.可选参数要放在参数列表的最后

//string p2="abc"为可选参数
void Dowrok(string p1, string p2="abc")
{
    // 代码块
}
View Code

5.Lambda表达式

①用Lambda表达式来声明方法:

//PicName()方法没有参数,返回一个字符串实例
public string PicName() => "tom";

//
public int Add(int a, int b) => a+b
View Code

②Lambda在委托中的使用

// 匿名方法
delegate int calculator(int x, int y); //委托
        static void Main()
        {
            calculator cal = delegate(int num1,int num2)
            {
                return num1 + num2;
            };
            int he = cal(1, 1);
            Console.Write(he);
        }

// Lambda实现
delegate int calculator(int x, int y); //委托类型
        static void Main()
        {
            calculator cal = (x, y) => x + y;//Lambda表达式
            int he = cal(1, 1);
            Console.Write(he);
        }
View Code

③.IEnumerable<>接口中使用Lambda

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace IEnumerable
{
    class Program
    {
        static void Main(string[] args)
        {
            List<string> frits = new List<string> { "apple", "passionfruit", "banana", "mango", "orange", "blueberry", "grape", "strawberry" };
            IEnumerable<string> query = frits.Where(fut => fut.Length < 6);
            foreach (string fut in query)
            {
                Console.WriteLine(fut);
            }

            Console.ReadKey();

        }


    }
}
View Code

6.析构函数:资源回收

 public class Test
    {
        // 构造函数
        public Test()
        {
            System.Diagnostics.Debug.WriteLine("构造函数被调用");
        }

        //析构函数
        ~Test()
        {
            System.Diagnostics.Debug.WriteLine("析构函数被调用");
        }
    }


//调用析构函数
static void Main(string[] args)
{
      Test t=new test();
}

            
View Code

7.程序资源释放的方法:

①析构函数

②实现IDisposable接口

public class Test : System.IDisposable
{
    //Dispose方法
    public void Dispose()
    {
        //带参数的Dispose方法,释放托管和非托管资源
        Dispose(true);
        //手动调用了Dispose释放资源,放弃析构函数,这里阻止了GC调用析构函数
        System.GC.SuppressFinalize(this);
    }

    //protected的Dispose方法,保证不会被外部调用。
    //传入bool值disposing以确定是否释放托管资源
    protected void Dispose(bool disposes)
    {
        if (disposes)
        {
            ///TODO:在这里加入清理"托管资源"的代码,应该是xxx.Dispose();
        }
        ///TODO:在这里加入清理"非托管资源"的代码
    }

    //供GC调用的析构函数
    ~TestClass()
    {
        Dispose(false);//释放非托管资源
    }
}
View Code

③using函数

using(Test t=new Test())
{
   //
}
View Code

8.结构:使用关键字“struct”定义

①在结构中声明字段时不能直接进行赋值

struct Pet
{
     //不能直接进行赋值:public string Name="tom"
     public string Name;
}
View Code

②通过new来实现实例

// 1.实现以上的类
Pet  p=new pet();
      p.Name="tom";

// 2.也可写成
Pet p;
      p.Name="tom";

// 3.当Pet类中存在方法体时必须使用new来创建实例
View Code

9.值类型与引用类型

①类属于引用类型:值随变量的变化而变化(引用实例的内存位置)

②结构属于值类型:值类型属于独立的类型,值之间只存在复制关系,修改一个值,另外一个值不会改变(开辟一个新的内存位置)

10.匿名方法:匿名方法是没有名称只有主体的方法;在匿名方法中不需要指定返回类型,它是从方法主体内的 return 语句推断的。

①匿名方法通过delegate 关键字创建委托实例来声明

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {
        //定义一个委托
        public delegate int SumAdd(int a, int b);
        static void Main(string[] args)
        {
            SumAdd sumAdd = delegate (int a, int b) { return a + b; };//把一个方法赋值给委托,其实这种写法就是匿名方法
            int result = sumAdd.Invoke(2, 2);
            Console.WriteLine(result);
            Console.ReadKey();

        }
    }
}
View Code

②Example

using System;

delegate void NumberChanger(int n);
namespace DelegateAppl
{
    class TestDelegate
    {
        static int num = 10;
        public static void AddNum(int p)
        {
            num += p;
            Console.WriteLine("Named Method: {0}", num);
        }

        public static void MultNum(int q)
        {
            num *= q;
            Console.WriteLine("Named Method: {0}", num);
        }

        static void Main(string[] args)
        {
            // 使用匿名方法创建委托实例
            NumberChanger nc = delegate(int x)
            {
               Console.WriteLine("Anonymous Method: {0}", x);
            };
            
            // 使用匿名方法调用委托
            nc(10);

            // 使用命名方法实例化委托
            nc =  new NumberChanger(AddNum);
            
            // 使用命名方法调用委托
            nc(5);

            // 使用另一个命名方法实例化委托
            nc =  new NumberChanger(MultNum);
            
            // 使用命名方法调用委托
            nc(2);
            Console.ReadKey();
        }
    }
}
View Code

11.方法重载:在类型内部允许存在相同名字的方法,但不能重复(参数不同)

①具有不同类型的返回值且参数有差异的同名方法阔以重载

public string Dowork(int a){}

public int Dowork(){}

//第一个返回string类型的带一个int类型参数,第二个返回int类型不带参数,类型参数不同,能构成重载
View Code

②参数列表的类型及顺序不同

void Test(string a){}

void Test(float a,double b){}
View Code

③针对ref与out

-1.一个方法带ref/out,则能构成重载

// ref
void Plen(ref short v){}
void Plen(short v){}


//out
void plen(short v){}
void plen(out short v){ v = 2 }
View Code

-3.ref与out不能构成重载

//编译报错,编译器不区分ref和out参数
void plen(ref short v){}
void plen(out short v){ v = 2 }
View Code

④构造函数中的重载

public class Test
{
      public Test(){}
      public Test(string Name){}
}
View Code

12.方法重写(重写改变父类方法,即调用子类方法):使用关键字virtual修饰的方法,叫虚方法;可以在子类中(继承至虚方法)声明同名的方法,叫重写,重写实现了多态

-1.重写:抽象方法,接口,标记为virtual的方法可以被重写(override),实方法不可以;

using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {
        
        static void Main(string[] args)
        {
            //调用虚方法
            C1 c1 = new C1();
            Console.WriteLine(c1.GetName());
            //调用重写方法
            C2 c2 = new C2();
            Console.WriteLine(c2.GetName());

            //用子类创建父类,new C2开辟新的空间来存放对应调用子类的方法
            C1 c3 = new C2();
            Console.WriteLine(c3.GetName());

            Console.ReadKey();

        }

        public class C1
        {
            public virtual string GetName()
            {
                return "实方法";
            }
        }
        public class C2:C1
        {
            public override string GetName()
            {
                return "重写的方法";
            }
        }
    }

}
View Code

13.在类中使用new关键字修饰的方法:①实现覆盖

-1.覆盖:仍然调用父类方法;虚方法、实方法都可以被覆盖(new),抽象方法,接口 不可以;

using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {
        
        static void Main(string[] args)
        {
            //调用虚方法
            C1 c1 = new C1();
            Console.WriteLine(c1.GetName());
            //调用覆盖方法
            C2 c2 = new C2();
            Console.WriteLine(c2.GetName());

            //在覆盖创建的基类中用子类创建父类,new C2仍然调用父类C1方法地址
            C1 c3 = new C2();
            Console.WriteLine(c3.GetName());

            Console.ReadKey();

        }

        public class C1
        {
            public virtual string GetName()
            {
                return "实方法";
            }
        }
        public class C2:C1
        {
            public new string GetName()
            {
                return "实现覆写的方法";
            }
        }
    }

}
View Code

14.静态方法:静态类与静态成员都使用关键字static来定义

①静态类只能定义静态成员

public static class Test()
{
    public static void SoyHelper(){}
    public static string Message{get; set;}  
}
View Code

15.c#委托:Action、 Action<T>、Func<T>、Predicate<T>

①什么叫委托??(类似c++的指针函数)

定义:委托是一个类,它定义了方法的类型,使得可以将方法当作另一个方法的参数来进行传递,这种将方法动态地赋给参数的做法,可以避免在程序中大量使用If-Else(Switch)语句,同时使得程序具有更好的可扩展性;用于实现事件和回调方法,所有的委托(Delegate)都派生自 System.Delegate 类。

②委托的声明语法:delegate关键字

delegate <return type> <delegate-name> <parameter list>

-1.声明带参的委托方法

/// <summary>
/// 委托和事件的应用
/// </summary>
/// <param name="name">声明带有一个string参数的方法,并返回一个int类型变量</param>

public delegate int MyDelegate(string name);
View Code

-2.委托的实例化:使用new关键字来创建

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Example_Delegate
{
    class Program
    {
        /// <summary>
        /// 委托和事件的应用
        /// </summary>
        /// <param name="args"></param>
        static void Main(string[] args)
        {
           
            Mydelegate d = new Mydelegate(Name);
            //使用委托对象调用方法
            d("tom");
        }
        //委托
        public delegate void Mydelegate(string name);

        public static void Name(string name)
        {

            Console.WriteLine("你好,我的名字叫" + name);
            Console.ReadKey();
        }

    }
}
View Code

③.委托的多播(通俗说就是增加附加方法体或减少附加的方法体,即:+ 或 - ;)

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;


namespace Example_Delegate
{
    class Program
    {
        public delegate int NumAppes(int n);
        static int a = 10;
        public static int AddNum(int p)
        {
            a += p;
            return a;
        }

        public static int MultNum(int q)
        {
            a *= q;
            return a;
        }

        public static int GetNum()
        {
            return a;
        }
        /// <summary>
        /// 委托和事件的应用
        /// </summary>
        /// <param name="args"></param>
        static void Main(string[] args)
        {
           //委托的实例
            NumAppes nc;
            NumAppes nc1 = new NumAppes(AddNum);
            NumAppes nc2 = new NumAppes(MultNum);
            nc = nc1;
            nc += nc2;

            // 调用多播
            nc(5);
            Console.WriteLine("Value of Num: {0}", GetNum());
            Console.ReadKey();
        }
      
    }
}
View Code

-1.多播的具体实例

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {
        //声明一个委托,即命令
        public delegate void Icecream();
        static void Main(string[] args)
        {
            //实现自己买根雪糕
            Icecream ic = new Icecream(Brother.Tiket);
            //实现再给弟弟附带买一根雪糕,同时实现两个买的动作
            ic += Brother.MyBrotherTiket;
            ic();
            Console.ReadKey();
        }
    }
    // 果果类
    public class Brother
    {
        public static void Tiket()
        {
            Console.WriteLine("给我自己买根雪糕!!");
        }

        public static void MyBrotherTiket()
        {
            Console.WriteLine("算了,好胸得,给弟弟也带一跟雪糕吧!");
        }
    }
}
View Code

-2.委托的多播实现

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {
        //声明一个委托,即命令
        public delegate int Icecream(int a, int b);

        static void Main(string[] args)
        {
            Icecream ic;
            Icecream ic1 = new Icecream(Brother.Multiply);
            Icecream ic2 = new Icecream(Brother.Sum);
            Icecream ic3 = new Icecream(Brother.Divide);
            ic = ic1; 
            ic += ic2;
            ic += ic3;
            int ret1 = ic.Invoke(10, 2);
            Console.WriteLine(ret1);
            Console.ReadKey();
        }
    }
    public class Brother
    {
        public static int Multiply(int a, int b)
        { return a * b;  }

        public static int Divide(int a, int b)
        { return a / b; }

        public static int Sum(int c, int d)
        { return c + d; }
    }


}
View Code

④Example_3

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.IO;

namespace Example_3
{
    class Program
    {
        static FileStream fs;
        static StreamWriter sw;

        public delegate void PrintString(string s);
        static void Main(string[] args)
        {
            PrintString p1 = new PrintString(WriteShow);
            PrintString p2 = new PrintString(WriteToFile);
            SendString(p1);
            SendString(p2);
            Console.ReadKey();
        }

        //打印搭配控制台
        public static void WriteShow(string s)
        {
            Console.WriteLine("this String is:{0}",s);
        }

        //改方法打印到文件
        public static void WriteToFile(string s)
        {
            fs = new FileStream("D:\\messge.txt", FileMode.Append, FileAccess.Write);
            sw = new StreamWriter(fs);
            sw.WriteLine(s);
            sw.Flush();
            sw.Close();
            fs.Close();
        }

        //把委托作为参数,并使用他调用方法
        public static void SendString(PrintString p)
        {
            p("Hello World !!");
        }
    }
}
View Code

 ⑤泛型委托(简化委托的定义)

-1.Action:Action委托没有参数,也没有返回值

(1)简单了解:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {
        // 定义Action委托
        public delegate void Action();
        static void Main(string[] args)
        {
            // 实例化Action委托
            Action a = new Action(Alt);
            a();
            Console.ReadKey();
        }

        public static void Alt()
        {
            Console.WriteLine("hao lo!!");
        }
    }

}
View Code

(2)Lambd表达式改写以上实例

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {
        
        static void Main(string[] args)
        {
            Action t = () => { Console.WriteLine("hao lo"); };
            t();
            Console.ReadKey();
        }

      
    }

}
View Code

(3)Action的多播

using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {

        public delegate void Action();
        static void Main(string[] args)
        {     
            Action a = new Action(Alt);
            a += AltS;
            a();
            Console.WriteLine();
            Console.ReadKey();

        }

        public static void Alt()
        {
            Console.WriteLine("hao lo!!");
        }
        public static void AltS()
        {
            Console.WriteLine("HO LO!!");
        }
    }

}
View Code

-2.Aciton<>:Action<>委托可传入<16个参数,无返回值

(1)简单了解:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {
        
        static void Main(string[] args)
        {
            //实例化Action<>委托
            Action<int, int> t = new Action<int, int>(Alt);
            t(3,3);
            Console.ReadKey();
        }
        public static void Alt(int a, int b)
        {
            Console.WriteLine(a + b);
        }
    }

}
View Code

(2)Lambd表达式改写以上实例

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {
        
        static void Main(string[] args)
        {
            Action<int, int> t = (a, b) => { Console.WriteLine(a + b); };
            t(3, 4);
            Console.ReadKey();
        }
       
    }

}
View Code

-3.Func<T>:Func<T>委托始终都会有返回值,返回值的类型是参数中最后一个

(1)简单了解:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {

        static void Main(string[] args)
        {
            //1
            Func<int, int, int> c1 = (int x, int y) => { return x + y; };
            int a = c1(2, 3);
            //2
            Func<int, int, int> c2 = (x, y) => { return x + y; };
            int b = c2(2, 2);
            //3
            Func<int, int, int> c3 = (x, y) => x + y;
            int c = c3(3, 3);

            Console.WriteLine("输出:{0},{1},{2}", a, b, c);
            Console.ReadKey();
        }

    }

}
View Code

(2)简单定义:最后一个参数都为返回值类型

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {
        static void Main(string[] args)
        {
            Func<int, int, bool> t = new Func<int, int, bool>(Su);
            bool result = t(3, 2);
            Console.WriteLine(result);
            Console.ReadKey();
           
        }
        public static  bool Su( int a, int b)
        {
            return a > b;
        }

    }

}
View Code

(3)Lambd表达式直接把方法定义在委托中:重新改写以上实例

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {
        static void Main(string[] args)
        {

            Func<int, int, bool> t = (a, b) => { return a > b; };
            bool result = t(3, 4);
            Console.WriteLine(result);
            Console.ReadKey();
        }

    }

}
View Code

 -4.Predicate<T>:Predicate<T>委托表示定义一组条件并确定指定对象是否符合这些条件的方法,返回值始终为bool类型 

(1)简单了解:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {
        
        static void Main(string[] args)
        {
            //委托
            Predicate<int> t = new Predicate<int>(Math);

            int[] arr = { 12, 45, 67, 43, 78, 90, 205 };
            int first = Array.Find(arr, t);
            Console.WriteLine(first);
            Console.ReadKey();
        }
        public static bool Math(int val)
        {
            return val > 60;
        }
    }

}
View Code

(2)Lambd表达式直接把方法定义在委托中:重新改写以上实例

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {
        
        static void Main(string[] args)
        {
            //委托
            Predicate<int> t = val => { return val>60; };
            int[] arr = { 12, 45, 67, 43, 78, 90, 205 };
            int first = Array.Find(arr, t);
            Console.WriteLine(first);
            Console.ReadKey();
        }

    }

}
View Code

(3)Predicate<T>实例

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {
        
        static void Main(string[] args)
        {
            int SetState = 1;
            int SetType = 1;
            Double price = 10.00;
            string[] TypeName = { "蔬菜", "水果" };
            List<VegType> t = new List<VegType>() {
            new VegType() { VegetablesType = "蔬菜", Name = "芹菜", Price = 10.00 },
            new VegType() { VegetablesType = "蔬菜", Name = "大白菜", Price = 3.00 },
            new VegType() { VegetablesType = "蔬菜", Name = "白萝卜", Price = 2.00 },
            new VegType() { VegetablesType = "蔬菜", Name = "花菜", Price = 13.00 },
            new VegType() { VegetablesType = "蔬菜", Name = "韭菜", Price = 8.00 },
            new VegType() { VegetablesType = "蔬菜", Name = "芹菜", Price = 10.00 },
            new VegType() { VegetablesType = "水果", Name = "桃子", Price = 16.00 },
            new VegType() { VegetablesType = "水果", Name = "苹果", Price = 14.00 },
            new VegType() { VegetablesType = "水果", Name = "车厘子", Price = 25.00 },
            new VegType() { VegetablesType = "其他", Name = "其他", Price = 28.00 },
            new VegType() { VegetablesType = "其他", Name = "其他", Price = 14.00 },
            new VegType() { VegetablesType = "其他", Name = "其他", Price = 25.00 },
            new VegType() { VegetablesType = "其他", Name = "其他", Price = 28.00 }
        };
        List<VegType> m = t.FindAll(new Predicate<VegType>(delegate(VegType veg)
            {
                bool Result = true;
                if (SetType==1)
                {
                    if (veg.Price<price)
                    {
                        Result = false;
                    }
                }
                if (SetState==1)
                {
                    if (veg.VegetablesType != TypeName[0])
                    {
                        Result = false;
                    }
                }
                return Result;
            }));
            m.ForEach(x => { Console.WriteLine("类型:{0},名称:{1},价格:{2}", x.VegetablesType, x.Name, x.Price); });
            Console.ReadKey();
            
        }
        public class VegType
        {
            public string VegetablesType { get; set; }
            public string Name { get; set; }
            public Double Price { get; set; }
        }

    }

}
View Code

16.Lambda表达式

①Lambda表达式常见写法

using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.IO;

namespace Example_3
{
    class Program
    {
      //委托
        public delegate int CalAdd(int a, int b);
        static void Main(string[] args)
        {
            //方法一
            CalAdd calAdd=(int a, int b) =>{ return a + b; };
            int result1 = calAdd.Invoke(2,2);
            Console.WriteLine(result1);
            //方法二
            CalAdd c = (a, b) => { return a + b; };
            int result2 = c(3, 3);
            Console.WriteLine(result2);
            //方法三
            CalAdd cl = (a, b) =>  a + b;
            int result3 = cl(4, 4);
            Console.WriteLine(result3);

            Console.ReadKey();
            
        }
}
View Code

②用Lambda表达式来声明方法:

//PicName()方法没有参数,返回一个字符串实例
public string PicName() => "tom";

//
public int Add(int a, int b) => a+b
View Code

③Lambda在委托中的使用

// 匿名方法
delegate int calculator(int x, int y); //委托
        static void Main()
        {
            calculator cal = delegate(int num1,int num2){return num1+num2;};
            int he = cal.Invoke(1, 1);
            Console.Write(he);
        }

// Lambda实现
delegate int calculator(int x, int y); //委托类型
        static void Main()
        {
            calculator cal = (x, y) => x + y;//Lambda表达式
            int he = cal(1, 1);
            Console.Write(he);
        }
View Code

 ④Lambda的表达式树:表达式树是存取Lambda表达式的一种数据结构;要使用Lambda表达式的时候,直接从表达式中获取出来,Compile()就可以直接用

using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace Example_3
{
    class Program
    {
        
        static void Main(string[] args)
        {
            Expression<Func<int, int, int>> p = (x, y) => x + y;
            Func<int, int, int> fun = p.Compile();
            int result = fun.Invoke(2, 2);
            Console.WriteLine(result);
            Console.ReadKey();
        }

    }

}
View Code

17.抽象方法和抽象类:使用关键字 abstract 来定义抽象类和抽象方法,同时抽象类不能被初始化,只提供部分实现

18.装箱与拆箱:需要装箱与拆箱的地方就是值类型与引用类型(值转引用为装箱,引用转值类为拆箱),装箱是一种通过将变量存储到System.Object中来显示的将值类型转化为引用类型的机制,当进行装箱操作时,CLR会将新对象分配到堆中,并将值类型的值复制到改实例中。

//装箱:
int a = 20;
object b = a;  //装箱

//拆箱:
int c = int(b) ; //拆箱,将引用类型转化为值类型,验证接收数据类型是否与装箱类型一致

19.泛型类:public class Student<T> { }

①.引用命名空间:System.Collection.Generic

②.System.Collection.Generic下核心类类型:

泛型类 描述
Collection

泛型集合的基类,可以比较两个泛型是否相等

Dictionary<TKey, TValue>

键值对的泛型集合

List

可动态调整列表项的大小

Queue

队列,先进先出(FIFO)列表的泛型表现

Stack

堆栈,后进先出(LIFO)列表的泛型表现

 

 

 

 

 

 

 

 

 

 

 

3.简单了解:

Test.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace IEnumerable
{
    class Test
    {
        public class Rustul<T>
        {
            // 定义一个长度为5的泛型
            T[] t = new T[5];
            int i = 0;

            public void Add(T item)
            {

                if (i + 1 < 6)
                {
                    t[i] = item;
                }
                i++;

            }

            // foreach语句迭代索引
            public T this[int index]
            {
                get { return t[index]; }
                set { t[index] = value; }
            }
        }
    }
}
View Code

Program.cs

using System;
using System.Collections.Generic;
using System.Text;

namespace IEnumerable
{
    class Program
    {
        static void Main(string[] args)
        {
            // 用整形来实例化泛型类
            Test.Rustul<int> Obj = new Test.Rustul<int>();
           // 向集合中添加数据
            Obj.Add(1);
            Obj.Add(2);
            Obj.Add(3);
            Obj.Add(4);   // 没有装箱操作,再泛型中指定了数据类型,在遍历
            Obj.Add(5);   //泛型集合中时会从编译器动态生成的类中将使用int类型。所以将不会发生装箱和拆箱

            // 遍历数据
            for (int i = 0; i < 5; i++)
            {
                Console.WriteLine(Obj[i]);  //没有拆箱操作
            }
            Console.ReadKey();
        }   
    }
}
View Code

 4.泛型的性能上:在定义范型对象的时候要明确指定传入时的具体类型,所以相同类型之间自然就不用装拆箱之类的操作了,所以泛型的性能是高于其他集合类型的(比如ArrayList)

using System;
using System.Collections;
using System.Collections.Generic;
using System.Text;

namespace IEnumerable
{
    class Program
    {
        static void Main(string[] args)
        {
            ArrayList t = new ArrayList();
            t.Add(50);   //装箱:值类型转引用
            t.Add("tom"); //装箱:值类型转引用


            int x = (int)t[0]; // 拆箱
            string n = (string)t[1];// 拆箱
            //int y = (int)t[1];  // 当使用int类型来接收strin类型时,出现System.InvalidCastException:“指定的转换无效。”

            //遍历打印 ArrayList
            foreach (var item in t)
            {
                Console.WriteLine(item);
            }
            Console.WriteLine($"拆箱后的值:{n}");
            //Console.WriteLine(y);
            Console.ReadKey();
        }   
    }
}
View Code

20.字典:

作用:允许基于关键字来访问元素的数据结构

特性:快速查询

典型的字典函数:Dictionary <TKey, TValue>, key表示关键字的类型,value表示可以存储的值

①.示例:

示例一:Dictionary 是二叉树式的存储结构,不支持用索引来取值,只能通过遍历

using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace IEnumerable
{
    class Program
    {
        static void Main(string[] args)
        {
            // 定义一个字典集合
            Dictionary<int, string> p = new Dictionary<int, string>(5);
            //向字典中添加类型
            p.Add(1, "A");
            p.Add(2, "B");
            p.Add(3, "C");
            p.Add(4, "D");
            p.Add(5, "E");

            //遍历输出
            for (int i = 1; i < p.Count; i++)
            {
                Console.WriteLine(p[i]);
            }

            //获取对应的key与value
            foreach (var key in p)
            {
                Console.WriteLine($"key:{key.Key},value:{key.Value}");
            }

            
            Console.WriteLine($"查询对应的key,如果不存在则进行创建:");
            if (!p.ContainsKey(6))
            {
                p.Add(6, "f");
            }

            Console.WriteLine($"通过key查找元素:");
            if (p.ContainsKey(1))
            {
                Console.WriteLine("key:{0},value={1}","1",p[1]);
                Console.WriteLine(p[1]);
            }

            Console.WriteLine($"得到哈希表键的集合:");
            Dictionary<int, string>.KeyCollection keyCol = p.Keys;
            foreach (var item in keyCol)
            {
                Console.WriteLine($"key={item}");
            }


            Console.WriteLine($"使用TryGetValue方法获取指定键对应的值:");
            string vol = string.Empty;
            if (p.TryGetValue(1, out vol))
            {
                Console.WriteLine($"找到数据的value:{vol}");
            }
            else
            {
                Console.WriteLine($"无数据!");
            }
            Console.ReadKey();

        }

        
    }
}
View Code

示例二:覆盖Object中的ToString()方法以显示特定员工的名称和奖金

emp.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace IEnumerable
{
    public class emp
    {
        private string name;
        private int salary;

        public emp(string name, int salary)
        {
            this.name = name;
            this.salary = salary;
        }

        //重写object中ToString方法
        public override string ToString()
        {
            StringBuilder sb = new StringBuilder(200); //当指定分配大小之后,性能就会得到提升。如果超过指定大小系统会当前大小倍增
            sb.AppendFormat("{0},{1}", name, salary);

            return sb.ToString();
        }
    }
}
View Code

Program.cs

using System;
using System.Collections.Generic;
using System.Text;

namespace IEnumerable
{
    class Program
    {
        static void Main(string[] args)
        {
            //定义一个字典集合 
            Dictionary<string, emp> dObj = new Dictionary<string, emp>(2);

            //向字典中添加元素
            emp tom = new emp("tom", 2000);
            dObj.Add("tom", tom);   // 键,值 
            emp john = new emp("jarr", 1500);
            dObj.Add("jarr", jarr);

            //print data  
            foreach (Object str in dObj.Values)
            {
                Console.WriteLine(str);
            }

            Console.ReadKey();
        }
    }
}
View Code

21.队列 (Queue):队列是一种特殊类型的容器,可确保以FIFO(先进先出)方式访问元素,其次队列集合最适合用来实现消息队列的传递组件

引用命名空间:using System.Collection

Queue 

 说明
Enqueue()

将对象添加到队列的末尾(逐一顺序添加队列)

 

Dequeue()

从队列的开头删除对象

 

Peek()

返回队列开头对象

 

 

 

 

 

 

 

 

 

 

 

 

 简单示例:

using System;
using System.Collections;
using System.Collections.Generic;
using System.Text;

namespace IEnumerable
{
    class Program
    {
        static void Main(string[] args)
        {
            // 定义一个队列
            Queue q = new Queue();

            q.Enqueue("tom");
            q.Enqueue(1);
            q.Enqueue(2);

            Console.WriteLine($"foreach循环:");
            foreach (var item in q)
            {
                Console.WriteLine(item);
            }

            Console.WriteLine($"while循环:");
            while (q.Count!=0)
            {
                Console.WriteLine(q.Dequeue());
            }

            Console.ReadKey();
        }   
    }
}
View Code

22.堆栈(Stack):Stack集合是LIFO的抽象(后进先出)

命名引用空间:using System.Collection

Stack函数集:

Stack

说明

Contains()

在集合中查找特定的元素,存在则返回true

 

Clear()

删除集合中的元素(清空集合)

 

Peek()

预览集合中的最新元素

 

Push()

将元素推入堆栈

 

Pop()

删除堆栈中的顶部元素并返回

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

简单示例:

using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace IEnumerable
{
    class Program
    {
        static void Main(string[] args)
        {
            //定义一个数组
            int[] Arrlist = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13 };
            //使用result来从小到大排序Arrlist数组
            int[] result = Arrlist.OrderByDescending(x => x).ToArray();

            //定义一个堆栈,将数组类型对象引用到堆栈集合中
            Stack s = new Stack(result);

            Console.WriteLine($"堆栈数:{s.Count}");

            Console.WriteLine($"foreach循环:");
            foreach (var item in s)
            {
                Console.WriteLine(item);
            }
            Console.WriteLine($"for循环:");

            for (int i = 0; i < s.Count; i++)
            {
                Console.WriteLine(s.Pop());
            }
            Console.ReadKey();
        }   
    }
}
View Code

使用Push()向堆栈集合中添加数据:

using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace IEnumerable
{
    class Program
    {
        static void Main(string[] args)
        {
            Stack s = new Stack();
            
            //向堆栈集合中添加数据
            for (int i = 0; i < 10; i++)
            {
                s.Push(i+1);
            }
            

            foreach (var item in s)
            {
                Console.WriteLine(item);
            }

            Console.ReadKey();
        }   
    }
}
View Code

23.异步编程:关键字asyncawait

异步理解:指在执行当前方法的同时,可以异步的去调用其他方法(异步方法),并且不会阻塞当前方法的线程

粗暴理解:同事执行多个方法,等待上一个方法执行完成后执行下一个方法

线程柱塞了解:那就是同步的时候,同步调用会阻塞线程,如果是要调用一项繁重的工作(如大量IO操作),可能会让程序停顿很长时间,造成糟糕的用户体验

委托方法示例:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Async
{
    public class Program
    {
        //委托方法
        public delegate int AddSum(int a, int b);
        public static void Main(string[] args)
        {
            Console.WriteLine("--同步调用--");
            AddSum add = new AddSum(Add);
            //委托的Invoke方法用来进行同步调用。同步调用也可以叫阻塞调用,
            //它将阻塞当前线程,然后执行调用,调用完毕后再继续向下进行。
            int result = add.Invoke(1, 2);

            Console.WriteLine("其他");

            Console.WriteLine(result);
            Console.ReadKey();
        }

        public static int Add(int a, int b)
        {
            Console.WriteLine("开始计算:" + a + "+" + b);
            Console.WriteLine("计算完成");
            return a + b;
        }
    }
}
View Code

①.async三种返回值:void、Task、Task<T>

②.async void:只能直接调用,与调用方法并行执行(同步)

③.async Task:可以直接调用,也可await调用,直接调用是并行执行(同步),await调用会等待执行完成(异步)

④.async Task<T>:只能通过await方式调用,获取T类型的返回值(异步)

示例一:同步下执行

using System;
using System.Collections;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace IEnumerable
{
    class Program
    {
        
        static void Main(string[] args)
        {
            // 使用async关键字
            Method();

            Setmoder();

            Console.ReadKey();
      
        }

        public static async  Task Method()
        {
            await Task.Run(() =>
            {
                for (int i = 0; i < 20; i++)
                {
                    Console.WriteLine($"Method:{i}");
                }
            });
        }

        public static void Setmoder()
        {
            for (int i = 0; i < 10; i++)
            {
                Console.WriteLine($"Setmoder:{i}");
            }
        }
    }
}
View Code

 输出:

 示例二:修改以上的示例,异步(要想异步执行等待,首先两个方法之间得存在依赖)

using System;
using System.Collections;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace IEnumerable
{
    class Program
    {
        
        static void Main(string[] args)
        {

            CallHelper();
            Console.ReadKey();
      
        }

        public static async void CallHelper()
        {
            Task<int> task = Method();

            //await关键字,等待Method执行完成后执行Setmoder方法
            int count = await task;
            Setmoder(count);

        }
        public static async Task<int> Method()
        {
            int count = 0;
            await Task.Run(() =>
            {
                for (int i = 0; i < 30; i++)
                {
                    Console.WriteLine($"Method:{i}");
                    count += 1;
                }
            });
            return count ;
        }

        //count参数依赖于Method中的count
        public static void Setmoder(int count)
        {
                Console.WriteLine($"Setmoder:循环的总数为{count}"); 
        }
    }
}
View Code

输出:

⑤常用的异步方法的Api:

HttpClient, SyndicationClient, StorageFile, StreamWriter, StreamReader, XmlReader, MediaCapture, BitmapEncoder, BitmapDecoder

获取文件字节大小的示例:

using System;
using System.Collections;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace IEnumerable
{
    class Program
    {
        
        static void Main(string[] args)
        {
            Task task = new Task(Method);
            task.Start();
            task.Wait();

            Console.WriteLine(1);
            Console.WriteLine(2);
            Console.WriteLine(3);
            Console.ReadKey();
        }
        static async void Method()
        {
            string FilePath = "C:\\数据处理.txt";
            Task<int> task = ReadFile(FilePath);

            int length = await task; // 使用等待关键字关键字await
            Console.WriteLine($"Total length:{length}");

            Console.WriteLine(1);
            Console.WriteLine(2);
        }

        private static async Task<int> ReadFile(string file)
        {
            int length = 0;
            using (StreamReader read=new StreamReader(file))
            {
                string s =await read.ReadToEndAsync();
                length = s.Length;
            }
            Console.WriteLine($"读取文件结束:{length}");
            return length;

            
            
        }
    }
}
View Code

⑥异步执行两个获取文件夹信息的实例

using log4net;
using log4net.Config;
using System;
using System.Collections.Generic;
using System.Configuration;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace DirPathFile
{
    class Program
    {
        static void Main(string[] args)
        {
            #region 获取文件夹目录下所有文件的完整路径
            var strPaths = ConfigurationManager.AppSettings["dirPath"];
            List<FileInfo> lst = new List<FileInfo>();
            List<FileInfo> lstfiles = GetInfo(strPaths, lst);
            DirectoryInfo info = new DirectoryInfo(strPaths);
            foreach (FileInfo item in lstfiles)
            {
                Console.WriteLine(item);
            }
            Console.WriteLine($"当前获取到的文件总数:{GetFilesCount(info)}");
            Console.WriteLine("--异步--");
            Thread.Sleep(3000);
            Task task = StepFile();
            Console.ReadKey();
            #endregion

            #region directoryinfo与directory说明
            //1.directory是公开建立、移动和全面列举目录和子目录的静态方法。
            //2.directoryinfo是公开建立、移动和全面列举目录和子目录的执行个体(Instance) 方法。
            //3.一个是公用的静态类,一个是实例类
            #endregion

            #region 获取指定目录包含的文件和子目录
            // 1.DirectoryInfo.GetFiles():获取目录中(不包含子目录)的文件,返回类型为FileInfo[],支持通配符查找;
            // 2.DirectoryInfo.GetDirectories():获取目录(不包含子目录)的子目录,返回类型为DirectoryInfo[],支持通配符查找;
            // 3.DirectoryInfo.GetFileSystemInfos():获取指定目录下(不包含子目录)的文件和子目录,返回类型为FileSystemInfo[],支持通配符查找;
            #endregion

            #region 获取指定文件的基本信息
            //1.FileInfo.Exists:获取指定文件是否存在;
            //2.FileInfo.Name,FileInfo.Extensioin:获取文件的名称和扩展名;
            //FileInfo.FullName:获取文件的全限定名称(完整路径);
            //FileInfo.Directory:获取文件所在目录,返回类型为DirectoryInfo;
            //FileInfo.DirectoryName:获取文件所在目录的路径(完整路径);
            //FileInfo.Length:获取文件的大小(字节数);
            //FileInfo.IsReadOnly:获取文件是否只读;
            //FileInfo.Attributes:获取或设置指定文件的属性,返回类型为FileAttributes枚举,可以是多个值的组合
            //FileInfo.CreationTime、FileInfo.LastAccessTime、FileInfo.LastWriteTime:分别用于获取文件的创建时间、访问时间、修改时间;
            #endregion

        }

        #region 采用异步
        public static async Task StepFile()
        {
            try
            {
                await Task.Run(() =>
                {
                    Console.WriteLine("--获取文件夹下的指定后缀文件--");
                    string strPath = @"E:\1\";
                    DirectoryInfo info = new DirectoryInfo(strPath);
                    List<FileInfo> lstfile = GetFile(strPath, ".jpg");
                    foreach (FileInfo item in lstfile)
                    {
                        Console.WriteLine(item);
                    }

                    Console.WriteLine($"当前获取到的文件总数:{GetFilesCount(info)}");
                   
                });
               
            }
            catch (Exception ex)
            {

                throw ex;
            }
        }
        #endregion

        #region 获取指定文件夹下的指定后缀文件

        /// <summary>
        /// 获取文件夹下的莫个后缀的所有文件
        /// </summary>
        /// <param name="path">文件路劲</param>
        /// <param name="ExtName">文件后缀</param>
        /// <returns></returns>
        public static List<FileInfo> GetFile(string path, string ExtName)
        {

            try
            {
                List<FileInfo> lst = new List<FileInfo>();
                string[] dir = Directory.GetDirectories(path);// 文件夹列表
                DirectoryInfo directoryInfo = new DirectoryInfo(path);
                FileInfo[] files = directoryInfo.GetFiles();
                if (files.Length != 0 || dir.Length != 0) // 当前目录文件或文件夹不能为空
                {
                    foreach (FileInfo f in files)
                    {
                        if (ExtName.ToLower().IndexOf(f.Extension.ToLower()) >= 0)
                        {
                            lst.Add(f);
                        }
                    }
                    foreach (string d in dir)
                    {
                        GetFile(d, ExtName);
                    }
                }
                return lst;
            }
            catch (Exception ex)
            {

                throw ex;

            }
        }
        #endregion


        #region 获取文件夹下所有文件的完整路径
        /// <summary>
        /// 获取文件夹下所有文件的完整路径
        /// </summary>
        /// <param name="path">路径</param>
        /// <param name="lst">返回参数</param>
        /// <returns></returns>
        private static List<FileInfo> GetInfo(string path, List<FileInfo> lst)
        {
            try
            {
                //string[] dirInfo = Directory.GetDirectories(path);
                string[] fileList = Directory.GetFileSystemEntries(path);
                foreach (string item in fileList)
                {
                    FileInfo fi = new FileInfo(item);
                    if (fi.Extension != " ") // 获取路径下的所有文件路径
                    {
                        lst.Add(fi);
                    }
                   
                }
                return lst;
            }
            catch (Exception ex)
            {

                throw ex;
            }
        }
        #endregion

        #region 获取当前目录下的文件总数
        /// <summary>
        /// 获取文件夹下的文件总数
        /// </summary>
        /// <param name="dirInfo"></param>
        /// <returns></returns>
        public static int GetFilesCount(DirectoryInfo dirInfo)
        {
            int totalFile = 0;
            totalFile += dirInfo.GetFiles().Length;
            foreach (DirectoryInfo f in dirInfo.GetDirectories())
            {
                totalFile += GetFilesCount(f);
            }
            return totalFile;
        }
        #endregion
  
    }
}
View Code

24.并行:Parallel

posted on 2019-07-20 16:43  ArSang-Blog  阅读(563)  评论(0编辑  收藏  举报