LINQ
LINQ介绍
语言集成查询 (LINQ) 是一组功能强大的技术,它基于将查询功能直接集成到 C# 语言中。 LINQ 查询是 C# .NET 中的第一类语言构造,就像类、方法、事件一样。LINQ 为查询对象 (LINQ to Objects)、关系数据库 (LINQ to SQL) 和 XML (LINQ to XML) 提供一致的查询体验。
为什么使用LINQ ?
为了理解为什么我们应该使用LINQ,让我们看一些例子。假设你想从一个Student对象数组中找出青少年学生的列表。
在C# 2.0之前,我们必须使用foreach
或for
循环来遍历集合以找到特定的对象。例如,我们必须编写以下代码,从年龄在12 ~ 20(青少年13 ~ 19)的学生数组中查找所有学生对象:
Example : C# 1.0中使用for循环从集合中查找元素
class Student
{
public int StudentID { get; set; }
public String StudentName { get; set; }
public int Age { get; set; }
}
class Program
{
static void Main(string\[\] args)
{
Student\[\] studentArray = {
new Student() { StudentID = 1, StudentName = "John", Age = 18 },
new Student() { StudentID = 2, StudentName = "Steve", Age = 21 },
new Student() { StudentID = 3, StudentName = "Bill", Age = 25 },
new Student() { StudentID = 4, StudentName = "Ram" , Age = 20 },
new Student() { StudentID = 5, StudentName = "Ron" , Age = 31 },
new Student() { StudentID = 6, StudentName = "Chris", Age = 17 },
new Student() { StudentID = 7, StudentName = "Rob",Age = 19 },
};
Student\[\] students = new Student\[10\];
int i = 0;
foreach (Student std in studentArray)
{
if (std.Age > 12 && std.Age < 20)
{
students\[i\] = std;
i++;
}
}
}
}
使用for循环很麻烦,不容易维护,也不容易读懂。C# 2.0引入了委托,可以用来处理这类场景,如下代码所示。
delegate bool FindStudent(Student std);
class StudentExtension
{
public static Student\[\] where(Student\[\] stdArray, FindStudent del)
{
int i\=0;
Student\[\] result = new Student\[10\];
foreach (Student std in stdArray)
if (del(std))
{
result\[i\] = std;
i++;
}
return result;
}
}
class Program
{
static void Main(string\[\] args)
{
Student\[\] studentArray = {
new Student() { StudentID = 1, StudentName = "John", Age = 18 } ,
new Student() { StudentID = 2, StudentName = "Steve", Age = 21 } ,
new Student() { StudentID = 3, StudentName = "Bill", Age = 25 } ,
new Student() { StudentID = 4, StudentName = "Ram" , Age = 20 } ,
new Student() { StudentID = 5, StudentName = "Ron" , Age = 31 } ,
new Student() { StudentID = 6, StudentName = "Chris", Age = 17 } ,
new Student() { StudentID = 7, StudentName = "Rob",Age = 19 } ,
};
Student\[\] students = StudentExtension.where(studentArray, delegate(Student std){
return std.Age > 12 && std.Age < 20;
});
}
}
}
因此,在C# 2.0中,您可以使用委托的优势来查找符合任何标准的学生。你不必使用for循环来查找使用不同条件的学生。例如,您可以使用相同的委托函数来查找StudentID为5或姓名为Bill的学生,如下所示:
Student\[\] students = StudentExtension.where(studentArray, delegate(Student std) {
return std.StudentID == 5;
});
//Also, use another criteria using same delegate
Student\[\] students = StudentExtension.where(studentArray, delegate(Student std) {
return std.StudentName == "Bill";
});
C#团队认为他们仍然需要使代码更加紧凑和可读。于是他们在C# 3.0中引入了扩展方法、Lambda表达式、表达式树、匿名类型和查询表达式。你可以使用C# 3.0的这些特性,它们是LINQ的构建块来查询不同类型的集合,并在单个语句中获得结果元素。下面的示例展示了如何使用带Lambda表达式的LINQ查询从学生集合中查找特定的学生。
Example : LINQ
class Program
{
static void Main(string\[\] args)
{
Student\[\] studentArray = {
new Student() { StudentID = 1, StudentName = "John", age = 18 } ,
new Student() { StudentID = 2, StudentName = "Steve", age = 21 } ,
new Student() { StudentID = 3, StudentName = "Bill", age = 25 } ,
new Student() { StudentID = 4, StudentName = "Ram" , age = 20 } ,
new Student() { StudentID = 5, StudentName = "Ron" , age = 31 } ,
new Student() { StudentID = 6, StudentName = "Chris", age = 17 } ,
new Student() { StudentID = 7, StudentName = "Rob",age = 19 } ,
};
// Use LINQ to find teenager students
Student\[\] teenAgerStudents = studentArray.Where(s => s.age > 12 && s.age < 20).ToArray();
// Use LINQ to find first student whose name is Bill
Student bill = studentArray.Where(s => s.StudentName == "Bill").FirstOrDefault();
// Use LINQ to find student whose StudentID is 5
Student student5 = studentArray.Where(s => s.StudentID == 5).FirstOrDefault();
}
}
正如您在上面的示例中看到的,我们在单个语句中使用LINQ运算符和Lambda表达式指定不同的标准。因此,LINQ使代码更加紧凑和可读,它还可以用于查询不同的数据源。例如,如果你在数据库中有一个学生表,而不是像上面那样有一个学生对象数组,你仍然可以使用相同的查询来使用实体框架查找学生。
LINQ的优点
熟悉的语言 : 开发人员不必为每种类型的数据源或数据格式学习新的查询语言。
编码更少 : 与更传统的方法相比,它减少了需要编写的代码量。
可读代码 : LINQ使代码更具可读性,因此其他开发人员可以轻松理解和维护它。
**查询多个数据源的标准化方式** : 相同LINQ语法可用于查询多个数据源。
查询的编译时安全性 : 它在编译时提供对象的类型检查。
智能感知支持 : LINQ为泛型集合提供智能感知。塑形数据:可以检索不同形状的数据。LINQ