在Enumerable类,针对IEnumerable数据,指的是内存数据
Linq 其实就是把对数据操作的通用部分完成,把可变的交给委托,使用者只用关心可变部分,其实Linq就是这么一个封装,但确实很好用.
我们通过反编译就能能清晰的看出
WHERE
Where:把对数据过滤的通用操作完成,把可变的过滤逻辑交给委托
Where是限制操作符,它将过滤标准应用在序列上,按照提供的逻辑对序列中的数据进行过滤。
Where操作符不启动查询的执行。当开始对序列进行遍历时查询才开始执行,此时过滤条件将被应用到查询中。
LINQ有两种方式实现,没有什么区别,主要是个人习惯。
示例1:
var list = studentList.Where<Student>(s => s.Age < 30);//陈述句 言出法随 封装的好
示例2(这里更类似于SQL语句,编译后会形成和示例1一样的形式):
Var list= from s in studentList
Where s.age<30
Select s;
SELECT 投影
Select:把对数据转化的通用操作完成,把可变的转换逻辑交给委托
示例:
{
//这里有一堆学生 每个学生都转换成别的对象
var list = studentList.Where<Student>(s => s.Age < 30)
//此处可以理解为,把上面筛选出的结果集再转换成
//另外一种类型
.Select(s => new
{
IdName = s.Id + s.Name,
ClassName = s.ClassId == 2 ? "高级" : "其他"
});
}
{
示例2:
var list = from s in studentList
where s.Age < 30
select new
{
IdName = s.Id + s.Name,
ClassName = s.ClassId == 2 ? "高级班" : "其他班"
};
}
以上两种方法,并没有存在任何差别,只是个人习惯,第一种称之为方法式,第二种称之为表达式形式
OrderBy和分页
类似于SQL,具体语法如下
var list = studentList.Where<Student>(s => s.Age < 30)//条件过滤
.Select(s => new//投影
{
Id = s.Id,
ClassId = s.ClassId,
IdName = s.Id + s.Name,
ClassName = s.ClassId == 2 ? "高级" : "其他"
})
.OrderBy(s => s.Id)//排序
//.ThenBy//2个都生效
.OrderByDescending(s => s.ClassId)//倒排 最后一个生效
.Skip(2)//跳过几条
.Take(3)//获取几条
;
group by
示例:
var list = from in studentList
where s.Age < 30
group s by s.ClassId into sg
//这里我们可以理解为分组之后的数据放到sg中去
select new
{
key = sg.Key,
maxAge = sg.Max(t => t.Age)
};
Join
需要注意,Linq中不能用==,只能用equals
示例:
var list = from s in studentList
join c in classList on s.ClassId equals c.Id//不能用==只能equals
select new
{
Name = s.Name,
CalssName = c.ClassName
};
左连接
需要注意:左连接需要把join的结果放入一个匿名类里
然后from sc in scList.DefaultIfEmpty()//
var list = from s in studentList
join c in classList on s.ClassId equals c.Id
into scList
from sc in scList.DefaultIfEmpty()//
select new
{
Name = s.Name,
CalssName = sc == null ? "无班级" : sc.ClassName//c变sc,为空则用
};