C#中Linq用法汇集

2023-11-16

C#中Linq常用用法

LINQ查询语法
有两种基本的方法来编写一个LINQ查询IEnumerable集合或IQueryable数据源。
1、查询语法或查询表达式语法
2、方法语法或方法扩展语法或Fluent

LINQ查询语法
查询语法与数据库的SQL(结构化查询语言)类似。它是在C#或VB代码中定义的。

具体的语法:

(1)从<范围变量>在<IEnumerable 或IQueryable 集合>
(2)<标准查询运算符> <lambda表达式>
(3)<select或groupBy运算符> <结果形成>

LINQ查询语法从关键字开始,以select关键字结束。以下是LINQ查询示例,它返回包含单词“Tutorials”的字符串集合。

在这里插入图片描述

查询语法从一个From子句开始,然后是一个Range变量。在从子句结构类似,意味着从集合中的每个对象。
它类似于一个foreach循环:"From> rangeVariableName in IEnumerablecollection"foreach(Student s in studentList)
在From子句之后,可以使用不同的标准查询运算符来过滤,分组和集合的元素。在LINQ中有大约50个标准查询操作符可用。在上图中,我们使用了“where”运算符(aka子句)后跟一个条件。这个条件通常用lambda表达式表示。
LINQ查询语法总是以Select或Group子句结束。Select子句用于形成数据。您可以按原样选择整个对象,也可以仅选择其中的一些属性。在上面的例子中,我们选择了每个结果字符串元素。

LINQ方法语法
方法语法(也称为流利语法)使用Enumerable或Queryable静态类中包含的扩展方法,类似于您将如何调用任何类的扩展方法。
————————————————
版权声明:本文为CSDN博主「Hi-Sunshine」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/zmh458/article/details/78935181

1、linq中交集、并集、差集的用法

简单的交集、并集、差集用法如下:

List<string> ListA = new List<string>();
List<string> ListB = new List<string>();
List<string> ListResult = new List<string>();

ListResult = ListA.Distinct().ToList();//去重
ListResult = ListA.Except(ListB).ToList();//差集
ListResult = ListA.Union(ListB).ToList();  //并集
ListResult = ListA.Intersect(ListB).ToList();//交集

若上面的例子不是List类型,而是List,则需要对XXXModel进行处理。
步骤如下:
(1)先定义Model。

public class ItemModel
{
    public string ItemCode { get; set; }
    public string ItemName { get; set; }
}

(2)定义如何Model间如何比较。若不定义,比较的是两个引用。

public class ItemModelComparer : IEqualityComparer<ItemModel>
    {
        //比较
        public bool Equals(ItemModel x, ItemModel y)
        {
            bool checkFlag = true;

            if (Object.ReferenceEquals(x, y))
            {
                checkFlag = true;
            }
            else if (Object.ReferenceEquals(x, null) || Object.ReferenceEquals(y, null))
            {
                checkFlag = false;
            }
            else
            {
                if (x.ItemCode == y.ItemCode)
                {
                    checkFlag = true;
                }
                else
                {
                    checkFlag = false;
                }
            }

            return checkFlag;

        }
    
        //实现获取哈希值
        public int GetHashCode(ItemModel model)
        {
            if (Object.ReferenceEquals(model, null)) return 0;

            int hashNurse = model.ItemCode.GetHashCode();

            return hashNurse;
        }
    
    }

(3)具体使用如下

List<ItemModel> ListA = new List<ItemModel>();
List<ItemModel> ListB = new List<ItemModel>();
List<ItemModel> ListResult = new List<ItemModel>();

ListResult = ListA.Distinct(new ItemModelComparer()).ToList();//去重
ListResult = ListA.Except(ListB, new ItemModelComparer()).ToList();//差集
ListResult = ListA.Union(ListB, new ItemModelComparer()).ToList();  //并集
ListResult = ListA.Intersect(ListB, new ItemModelComparer()).ToList();//交集

2、 join的用法

若出现两个List,想用Linq进行查询。则可以使用如下的方式

int tempSatisfiedConditionCount = (from r1 in whiteList
                                   join r2 in args.DiagList on r1.DiagCode equals r2.DiagCode
                                   select r1).Count();

多条件的join

//多条件的联合查核
List<DiagControlModel> whiteDiagList = (from r1 in diagControlList
        where r1.ControlRelation == 1
        join r2 in args.DiagList on new { code = r1.DiagCode, name = r1.DiagName }
        equals new{code=r2.DiagCode,name=r2.DiagName}
        select r1).ToList<DiagControlModel>();

另外,join还可以用于左连接/右连接

var LeftJoin = from emp in ListOfEmployees
                join dept in ListOfDepartment
                 on emp.DeptID equals dept.ID into JoinedEmpDept
                from dept in JoinedEmpDept.DefaultIfEmpty()
                 select new
                      {
                            EmployeeName = emp.Name,
                            DepartmentName = dept != null ? dept.Name : null
                      };

3、let用法

let是一个在linq中定义局部变量
1、可以有多个let子句
2、let后的变量无需声明类型
参见下例:

var query = from a in list  
                        let b = a.Name.Split('-')  
                        let c=a.Age  
                        where b[0] =="zhangs" & c>21  
                        select a; 

4、分组

常用的分组用法

      var linqtest = from r in db.Am_recProScheme
                     orderby r.rpId descending
                     group r by r.recType into n
                     select new
                     {
                         n.Key,  //这个Key是recType
                         rpId = n.Sum(r => r.rpId), //组内rpId之和
                         MaxRpId = n.Max(r => r.rpId),//组内最大rpId
                         MinRpId = n.Min(r => r.rpId), //组内最小rpId
                     };

略微复杂点:

	             var dataList= (from r in drugLabelList
                                    group r by new
                                    {
                                        r.OrderNo,
                                        r.PatientID,
                                        r.PatientName
                                    } into q
                                    let drugAmount = q.Sum(t => Convert.ToInt32(t.ChargeAmount))
                                    where drugAmount >= 0
                                    select new PrintDrugLabelModel
                                    {
                                        OrderNo = q.Key.OrderNo,
                                        PatientID = q.Key.PatientID,
                                        PatientName = q.Key.PatientName,
                                        ChargeAmount = ""+drugAmount
                                    }).ToList<PrintDrugLabelModel>();


//1
            var ss = from r in db.Am_recProScheme
                     orderby r.rpId descending
                     group r by r.recType into n
                     select new
                     {
                         n.Key,  //这个Key是recType
                         rpId = n.Sum(r => r.rpId), //组内rpId之和
                         MaxRpId = n.Max(r => r.rpId),//组内最大rpId
                         MinRpId = n.Min(r => r.rpId), //组内最小rpId
                     };
            foreach (var t in ss)
            {
                Response.Write(t.Key + "--" + t.rpId + "--" + t.MaxRpId + "--" + t.MinRpId);
            }
            //2
            var ss1 = from r in db.Am_recProScheme
                     orderby r.rpId descending
                     group r by r.recType into n
                     select n;
            foreach (var t in ss1)
            {
                Response.Write(t.Key + "--" + t.Min(p => p.rpId));
            }
            //3
            var ss2 = db.Am_recProScheme.GroupBy(p => p.recType);
            foreach (var t in ss2)
            {
                Response.Write(t.Key + "--" + t.Min(p => p.rpId));
            }
            //4
            string sssql = "select recType,min(rpId),max(rpId),sum(rpId) from Am_recProScheme group by recType";           //多字段 var result = (from item in data                          group item by new { item.Name, item.Type } into items                          select new                          {    items.Key.Name,    items.Key.Type,    Cnt = items.Count()                          }).ToList();            var s = data.GroupBy(p => new { p.Type, p.Name }).Select(p=>new {          p.Key.Type,          p.Key.Name,          cnt=p.Count()            }).ToList();

5、简单的函数计算

      var linqtest = (from r in db.Am_recProScheme
                      select r).Sum(p => p.rpId);

6、排序order by desc/asc

     var linqtest = (from r in db.Am_recProScheme
                     where r.rpId > 10
                     orderby r.rpId descending  //倒序
                     // orderby r.rpId, r.rpname descending   //多条件的倒序(与SQL语句中的相同)
                     //  orderby r.rpId ascending   //正序
                     select r);

7、top(1)

            //如果取最后一个可以按倒叙排列再取值
      var linqtest = (from r in db.Am_recProScheme                     
                      select r).FirstOrDefault();

8、跳过前面多少条数据取余下的数据

      var linqtest = (from r in db.Am_recProScheme
                      where r.rpId > 10
                      orderby r.rpId descending
                      select r).Skip(10).Take(10); //取第11条到第20条数据  

9、包含

	   //可以使用List、Array、string的Contains()方法进行判断
     var linqtest = (from r in db.Am_recProScheme
                     where r.SortsText.Contains("张")
                     select r);

10、连接查询

 var linqtest = (from r in db.Am_recProScheme
                 join w in db.Am_Test_Result on r.rpId equals w.rsId
                 orderby r.rpId descending
                 select r);

11、使用linq查询DataTable

            //遍历DataTable,将其中的数据对应到ClientStruct中:  
            List<ClientStruct> list = (from x in dtTable.AsEnumerable()  
                                       orderby x.Field<string>("")  descending  
                                       where x.Field<string>("ErrorType") == "漏孔" 
                                       select new ClientStruct  
                                       {  
                                           ID = x.Field<string>(cs.ID),  
                                           Name = x.Field<string>(cs.Name),  
                                           Company = x.Field<string>(cs.Company),  
                                           CreatedDate = x.Field<string>(cs.CreatedDate)  
                                       }).ToList<ClientStruct>();  

12、linq中列传行操作(Aggregate的使用)—2022-3-4

解决分组又聚合的问题。
后台数据存储的样式是:

在这里插入图片描述
希望实现:
在这里插入图片描述
即:实现分组,并且能将诊断进行聚合(列转行)
linq的写法如下:

var data_list = (from r in temp_result_list
                 group r by new
                      {
                          r.DrugCode,
                          r.VisitType
                      } into q
                  select q.Aggregate(temp_result_list[0],(workingSentence, next) => new DiagControlModel
                  {
                      DrugCode = q.Key.DrugCode,
                      VisitType = q.Key.VisitType,
     								DiagInfoStr =  workingSentence.DiagInfoStr + ";" + next.DiagName
                  })).ToList<DiagControlModel>();

13.分页数据查询

//1
            var ss = (from r in db.Am_recProScheme
                      where r.rpId > 10
                      orderby r.rpId descending
                      select r).Skip(10).Take(10); //取第11条到第20条数据                   

            //2 Take(10): 数据从开始获取,获取指定数量(10)的连续数据
            var ss1 = db.Am_recProScheme.OrderByDescending(p => p.rpId).Where(p => p.rpId > 10).Skip(10).Take(10).ToList();
            //3
            string sssql = "select * from  (select ROW_NUMBER()over(order by rpId desc) as rowNum, * from [Am_recProScheme]) as t where rowNum>10 and rowNum<=20";

14.sql中的In

//1
            var ss = from p in db.Am_recProScheme
                              where (new int?[] { 24, 25,26 }).Contains(p.rpId)
                              select p;
            foreach (var p in ss)
            {
                Response.Write(p.Sorts);
            }
            //2
            string st = "select * from Am_recProScheme where rpId in(24,25,26)";

15.多条件联合

这样写会报错,原因是名称不一样

new { 存货申请.cVouch_id, 存货申请.ccode, 存货申请.inid } equals
 new { OutAndInDonees.CVouch_Id, OutAndInDonees.MItemCode, OutAndInDonees.I_id }

修改如下:

on new { cVouch_id=存货申请.cVouch_id, ccode= 存货申请.ccode , 存货申请.inid } equals 
new { cVouch_id= OutAndInDonees.CVouch_Id, ccode=OutAndInDonees.MItemCode, inid= OutAndInDonees.I_id }


16.什么是多表连接查询

一:编写多表查询语句–内连接

对应SQL语句:

select * from Person  join Telephone on Person.Id = Telephone.PersonId

在这里插入图片描述
第一种方式:LINQ语法

       public List<Twotable> GetTwo()
        {
            var query = from a in   _entityRepository.GetAll()
                        join b in _TelRepository.GetAll()
                        on a.Id equals b.PersonId
                        select new Twotable{
                            Name=a.Name,
                            Telephone=b.PhoneNumber
                        };
            return query.ToList();
        }

第二种方式:Lambda语法

        public List<Twotable> GetTwo()
        {
            var query = _entityRepository.GetAll()
        .Join(
                _TelRepository.GetAll(),
        top => top.Id,
        art => art.PersonId,
        (top, art) => new Twotable
        {
            Name = top.Name,
            Telephone = art.PhoneNumber
        });
            return query.ToList();
        }

二:编写多表连接查询–左右连接

  • 左连接的概念:

对应SQL语句:

select * from Person  left join Telephone on Person.Id = Telephone.PersonId

在这里插入图片描述
在这里插入图片描述
方法1:LINQ语法

var leftOuterJoin = from a in _entityRepository.GetAll()
                       join b in _TelRepository.GetAll()
                        on a.Id equals b.PersonId
                        into cls from c in cls.DefaultIfEmpty()
                        select new Twotable
                        {
                            Name = a.Name,
                            Telephone = c.PhoneNumber
                        };

方法2:Lambda语法

       var leftOuterJoin = _entityRepository.GetAll()
      .GroupJoin(
              _TelRepository.GetAll(),
      top => top.Id,
      art => art.PersonId,
      (top, art) => new Twotable
      {
          Id = top.Id,
          Name = top.Name,
          Telephone =  art.FirstOrDefault(x => x.PersonId == top.Id).PhoneNumber
 
      }).Select(o => o);
  • 右连接的概念:

对应SQL语句:

select * from Person  right join Telephone on Person.Id = Telephone.PersonId

在这里插入图片描述

三:编写多表连接查询—全连接

全连接的概念

对应SQL语句

select * from Person full outer join Telephone on Person.Id = Telephone.PersonId

在这里插入图片描述
在这里插入图片描述
使用全连接:(合并左右连接就可以了)

      //右连接
            var rightOuterJoin = from b in _TelRepository.GetAll()
                        join a in _entityRepository.GetAll()
 
                          on b.PersonId equals a.Id
                          into cls
                        from c in cls.DefaultIfEmpty()
                        select new Twotable
                        {
                            Id = c.Id,
                            Name = c.Name,
                            Telephone = b.PhoneNumber
                        };
     //左连接
 
           var leftOuterJoin = from a in _entityRepository.GetAll()
                        join b in _TelRepository.GetAll()
                        on a.Id equals b.PersonId
                        into cls from c in cls.DefaultIfEmpty()
                        select new Twotable
                        {
                            Name = a.Name,
                            Telephone = c.PhoneNumber
                        };
var fullOuterJoin = leftOuterJoin.Union(rightOuterJoin);

或者

番外:

如果想 3表 或 4表 连接,那就和SQL语句一样在下面加 join就好了

var fullOuterJoin = leftOuterJoin.Concat(rightOuterJoin);
     var query = from b in _TelRepository.GetAll()
                        join a in _entityRepository.GetAll()
                          on b.PersonId equals a.Id
                          into cls
                        from c in cls.DefaultIfEmpty()
 
                          join d in _userRepository.GetAll()
                           on c.Id equals  d.Id
                            from e in cls.DefaultIfEmpty()
 
                        select new Twotable
                        {
                            Id = c.Id,
                            //Name = c.Name,
                            Name =e.Name,
                            Telephone = b.PhoneNumber
                        };
create proc *****
@GoodsId int,
@Number int,
@StockPrice money,
@SupplierId int,
@EmpId int,
@StockUnit varchar(50),
@StockDate datetime,
@TotalMoney money ,
@ActMoney money ,
@baseId int,
@Description nvarchar(255)
as
  declare @error int =0 --事务中操作的错误记录
  --开启事务
  begin transaction
    --实现进货信息的添加
    insert into StockInfo values(@GoodsId, @Number, @StockPrice, @SupplierId, @EmpId, @StockUnit, @StockDate, @TotalMoney, @ActMoney,DEFAULT,@Description, @baseId)
    set @error+=@@ERROR --记录有可能产生的错误号 
    --获取当前进货信息的标识列
    --判断当前商品有没有进货记录
    if exists (select * from dbo.InventoryInfo where goodid=@GoodsId) --说明记录存在,直接修改库存数量
      begin
        update dbo.InventoryInfo set GNumber=GNumber+@Number,TotalMoney+=@TotalMoney where goodid=@GoodsId
        set @error+=@@ERROR --记录有可能产生的错误号     
    end 
    else --这个商品从来没有过进货记录,那么就应该添加新的存在信息
      begin
        declare @GWarningNum int --此商品的预警数量
        --获取预警数量
        set @GWarningNum=(select WaringNum from dbo.GoodsInfo where GId=@GoodsId)
        insert into   dbo.InventoryInfo values(@GoodsId,@Number,@baseId,@GWarningNum,@TotalMoney,'第一次进货',default)
        set @error+=@@ERROR --记录有可能产生的错误号     
      end
--判断事务的提交或者回滚
if(@error<>0)
  begin
    rollback transaction
    return -1 --设置操作结果错误标识
  end
else
  begin
    commit transaction
    return 1 --操作成功的标识
  end
go
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

C#中Linq用法汇集 的相关文章

随机推荐

  • Elasticsearch Split和shrink API

    背景 尝试解决如下问题 单分片存在过多文档 超过lucene限制 分析 1 一般为日志数据或者OLAP数据 直接删除索引重建 2 尝试保留索引 生成新索引 数据写入新索引 查询时候包含 old index new index 3 尝试spl
  • 2023年第十四届蓝桥杯大赛python组省赛真题(已更新完)

    本篇更新蓝桥杯省赛真题的后5道 6 试题 F 公因数匹配 时间限制 10 0s 内存限制 512 0MB 本题总分 15 分 问题描述 给定 n 个正整数 Ai 请找出两个数 i j 使得 i lt j 且 Ai 和 Aj 存在大于 1 的
  • 线程(Linux系统实现)

    目录 1 线程概述 2 主线程和子线程 3 创建线程 线程函数 创建线程示例 4 线程退出 线程退出的原理主要包括以下两个方面 5 线程回收 回收子线程数据 6 线程分离 7 线程取消 8 线程 ID 比较 1 线程概述 线程是轻量级的进程
  • SIFT特征简介

    过程 1 尺度空间建立及极值点搜索 初步搜索 2 关键点精确定位 直线拟合使得关键点精确定位 x y sigma 消除边缘响应 初步搜寻特征点后 得到特征点的层数 像素坐标 x y 方向 文中分为18或36个离散方向 1 SIFT算法具的特
  • python dict遍历性能,Python:遍历list vs over dict items效率

    这取决于您使用的是哪个版本的Python 在Python 2中 some dict items 创建一个新的列表 这将占用一些额外的时间并占用更多的内存 另一方面 一旦创建了列表 它就是一个列表 因此在完成列表创建的开销之后 应该具有相同的
  • 用户行为路径数据埋点方案设计案例

    用户行为路径数据埋点方案设计案例 案例背景 业务需要对用户行为进行数据分析 现缺失这部分数据 需要设计采集方案获取数据满足业务分析需求 定义 数据采集方案是为埋点所设计的采集方案 所谓埋点就是在产品 通常是网页 app 中需要提取数据的地方
  • 小程序上传线上地址文件

    web上传的时候可以使用new Blob 但是在小程序中不能使用 当时的文件还是二进制的文件流 小程序上传不能使用线上地址 后来想了很多办法 最后把文件流使用wx saveFile先保存到本地 拿到result savedFilePath的
  • FPGA基础知识点

    FPGA知识点 Verilog基础语法 基础知识 逻辑值 逻辑0 表示低电平 也就是对应电路GND 逻辑1 表示高电平 也就是对应电路VCC 逻辑X 表示未知 有可能是高电平也有可能是低电平 逻辑Z 表示高阻态 外部没有激励信号 是一个悬空
  • Docker第七回(私有Registry)

    一 Docker Registry的分类 Registry用来保存docker镜像 包括镜像的层次结构和元数据 用户可以自建Registry 也可以使用官方的docker hub Sponsor Registry 第三方的Registry
  • 如何解决fiddler抓包时出现443的问题

    之前公司的app使用的http协议 因此不需要安装证书也能够转包 后来改成https协议后 在使用fiddler进行抓包时 一直出现tunnel to 443 百度了好久也没有具体的解决办法 后来发现需要在手机端安装fiddler的证书才行
  • stylefeng 文档_基于SpringBoot+spring mvc+Mybatis+beetl+bootstrap实现的简洁开源网站后台管理系统Guns...

    package com stylefeng guns config import io swagger annotations ApiOperation import org springframework boot autoconfigu
  • 面经——嵌入式常见面试题总结100题(上)

    参考 嵌入式常见面试题总结 1 作者 天泉证道 发布时间 2018 11 08 09 33 43 网址 https guoyanzhang blog csdn net article details 83855895 目录 1 字符型驱动设
  • oracle nvl函数

    1 nul函数将一个null值转换为一个实际的值 数据类型可以是日期 数字 字符 数据类型必须匹配 nvl commision 0 nvl hiredate 01 JAN 87 nvl job id no manager nvl to ch
  • 西电机器学习简答题核心考点汇总(期末真题,教材西瓜书)

    文章目录 前言 一 机器学习和深度学习区别以及原因 二 卷积核 池化层作用 三 SVM转化为对偶问题的优点 四 核函数的作用 五 特征的相似度定义 性质 六 预剪枝与后剪枝优缺点 七 密度直接可达 密度可达 密度相连定义 八 DBSCAN相
  • 前端:上传图片upload组件(传formData格式,后端返回图片文件流)

    使用组件 iview中的upload组件 html
  • 深入理解Flink的水位线

    Apache Flink是一个流处理框架 它支持事件时间和处理时间的概念 在处理流数据时 Flink通过水位线 Watermark 来追踪事件时间的进度 从而支持事件时间的操作 水位线是一种特殊的事件 它表示在此时间戳之前的所有事件都已经到
  • java八股文合集(附免费0积分下载链接)

    下面是地址 Java八股文一 java基础知识 Java八股文二 java集合框架 Java八股文三 Java多线程 Java八股文四 Java虚拟机 Java八股文五 MySQL Inno DB Java八股文六 spring相关 Jav
  • Python项目开发

    今天任务 1 创建Python项目为pythontest1以及test1 py文件 2 修改字号 3 输入九九乘法表程序 编译调试执行 4 配置全局pip镜像为阿里镜像 5 命令行中下载安装pygame包 新建项目 选择 Create Ne
  • Python解决OpenCV系列库安装报错问题

    1 pip install dlib 这个库的安装很大概率出现问题 可以去参考 Python dlib 无需编译安装 dlib 19 23 0 cp39 cp39 win amd64 whl 这里放一个百度网盘的链接 要求Python3 9
  • C#中Linq用法汇集

    C 中Linq常用用法 LINQ查询语法 有两种基本的方法来编写一个LINQ查询IEnumerable集合或IQueryable数据源 1 查询语法或查询表达式语法 2 方法语法或方法扩展语法或Fluent LINQ查询语法 查询语法与数据