【C#】LINQ学习笔记
LINQ(Language Integrated Query)全称基于关系数据的 .NET 语言集成查询,用于以对象形式管理关系数据,并提供了丰富的查询功能,它和Linq to xml、Linq to objects、Linq to dataset、Linq to entities等组成了强大的LINQ。
LINQ是C# 3.0引入的新特性,C#3.0也引入了其他一些新特性,以更好的使用LINQ,LinQ说白了就是使我们可以更方便更快捷的操作集合
1、基础特性
1、自动属性
public class Student { public int Id { get; set; } public string Name { get; set; } }
2、对象初始化器
Student toroto = new Student {Id = 1, , Name = "toroto"}; Student bomo = new Student {Id = 2, , Name = "bomo"};
3、集合初始化器
List<Student> students = new List<Student> { new Student {Id = 1, Name = "toroto"}, new Student {Id = 2, Name = "bomo"} }; Dictionary<string, Student> dictionary = new Dictionary<string, Student> { {"toroto", new Student {Id = 1, Name = "toroto"}}, {"bomo", new Student {Id = 2, Name = "bomo"}} };
4、隐式类型
//编译器自动根据上下文判断类型,变量不能初始为null var i = 10; var f = 10.5f; var b = true; var student = new Student(); var list = new List<Student>();
5、匿名类型对象
//创建匿名类型的对象,该对象有两个属性(Id,Name)(注意:不是Student类型) var stu = new {Id = 1, Name = "toroto"};
6、Lambda表达式(匿名函数)
(参数列表) => {函数体} 如: (a, b) => { return a + b; };
7、扩展方法(需要.Net 3.5)
////扩展方法类:必须为非嵌套,非泛型的静态类 public static class DatetimeEx { //通过this声明扩展的类,这里给DateTime类扩展一个Show方法,只有一个参数 public static void Show(this DateTime date, string msg) { Console.WriteLine("扩展方法调用"); Console.WriteLine(msg); } }
这样DateTime类就多了一个Show()方法了
2、LinQ To Object
接下来才是重点,LinQ的使用很简单,很简洁明了,查询到的结果使用 foreach 遍历
首先定义几个集合,用于下面查询
public class Student { public int Id { get; set; } public int Age { get; set; } public int ClassNum { get; set; } public string Name { get; set; } }
var students = new List<Student> { new Student {Id = 2, Age = 22, ClassNum = 2, Name = "bomo"}, new Student {Id = 1, Age = 21, ClassNum = 1, Name = "toroto"}, new Student {Id = 3, Age = 19, ClassNum = 2, Name = "tobi"}, new Student {Id = 4, Age = 20, ClassNum = 1, Name = "cloud"} };
1、简单查询
//从studnets中选择年龄>20的学生,并按降序排列 var res = from student in students //选择集合 where student.Age > 20 //条件 orderby student.Age descending //升序:ascending 降序:descending select student; //结果集合 foreach (var student in res) Console.WriteLine("{0}:{1}", student.Name, student.Age);
2、分组查询(使用了匿名类型对象)
//学生按ClassNum分组 var groups = from student in students group student by student.ClassNum into Class select new { Students = Class, ClassNum = Class.Key }; //第一次遍历到分组,第二次遍历才是学生 foreach (var group in groups) { Console.WriteLine("Class {0}:", group.ClassNum); foreach (var student in group.Students) { Console.WriteLine(student.Name); } }
3、多条件排序
//先按班级排序(升序),班级相同则按年龄排序(降序) var res = from student in students orderby student.ClassNum ascending, student.Age descending select student; foreach (var student in res) Console.WriteLine("Name:{0}, Age:{1}, ClassNum:{2}", student.Name, student.Age, student.ClassNum);
4、多集合查询
int[] numbersA = {0, 2, 4, 5, 6, 8, 9}; int[] numbersB = {1, 3, 5, 7, 8}; //多个集合的比较,相当于多重遍历 var pairs = from a in numbersA from b in numbersB let diff = Math.Abs(a-b) //中间值/额外值 或 操作 where a < b select new {a, b, diff = diff}; foreach (var pair in pairs) Console.WriteLine("{0}>{1}:{2}", pair.a, pair.b, pair.diff);
5、连接查询
定义两个类
public class Student { public int Id { get; set; } public int Age { get; set; } public int ClassNum { get; set; } public string Name { get; set; } } public class Score { public int Id { get; set; } public int ChineseScore { get; set; } public int MathScore { get; set; } public int EnglishScore { get; set; } }
使用 join 查询
var students = new List<Student> { new Student {Id = 1, Age = 21, ClassNum = 1, Name = "toroto"}, new Student {Id = 2, Age = 22, ClassNum = 2, Name = "bomo"}, new Student {Id = 3, Age = 19, ClassNum = 2, Name = "tobi"}, new Student {Id = 4, Age = 20, ClassNum = 1, Name = "cloud"} }; var scores = new List<Score> { new Score { Id = 1, ChineseScore = 77, MathScore = 80, EnglishScore = 85}, new Score { Id = 2, ChineseScore = 40, MathScore = 90, EnglishScore = 75}, new Score { Id = 3, ChineseScore = 68, MathScore = 30, EnglishScore = 80}, new Score { Id = 4, ChineseScore = 85, MathScore = 100, EnglishScore = 88}, }; var res = from student in students join score in scores on student.Id equals score.Id select new {Student = student, Score = score}; foreach (var student in res) { Console.WriteLine("{0}:ChineseScore:{1}, MathScore:{2}, EnglishScore:{3}", student.Student.Name, student.Score.ChineseScore, student.Score.MathScore, student.Score.EnglishScore); }
6、分组连接查询
var students = new List<Student> { new Student {Id = 1, Age = 21, ClassNum = 1, Name = "toroto"}, new Student {Id = 2, Age = 22, ClassNum = 2, Name = "bomo"}, new Student {Id = 3, Age = 19, ClassNum = 2, Name = "tobi"}, new Student {Id = 4, Age = 20, ClassNum = 1, Name = "cloud"} }; var scores = new List<Score> { new Score { Id = 1, ChineseScore = 77, MathScore = 80, EnglishScore = 85}, new Score { Id = 1, ChineseScore = 87, MathScore = 90, EnglishScore = 95}, new Score { Id = 2, ChineseScore = 40, MathScore = 90, EnglishScore = 75}, new Score { Id = 3, ChineseScore = 68, MathScore = 30, EnglishScore = 80}, new Score { Id = 4, ChineseScore = 85, MathScore = 100, EnglishScore = 88}, }; var res = from student in students join score in scores on student.Id equals score.Id into Sco select new {Student = student, Score = Sco}; foreach (var student in res) { Console.WriteLine("{0}:", student.Student.Name); foreach (var score in student.Score) { Console.WriteLine("ChineseScore:{0}, MathScore:{1}, EnglishScore:{2}", score.ChineseScore, score.MathScore, score.EnglishScore); } }
由于数据库不是很熟,所以这里只记录LinQ To Object,应该很多操作都是相同的,下次在写LinQ To SQL
LinQ还有使用函数查询的操作,内容比较多,明天再写,今天就写到这里