一、LINQ查询的数据源

  从应用程序的角度来看,原始源数据的特定类型和结构并不重要。 应用程序始终将源数据视为 IEnumerable<T> 或 IQueryable<T> 集合。

例如在 LINQ to XML 中,源数据显示为 IEnumerable<XElement>。所以要对某个对象应用LINQ查询,该对象必须实现 IEnumerable<T> 或 IQueryable<T> 。

  其中,数组类型并为实现 IEnumerable<T> 或 IQueryable<T> ,为什么也可进行LINQ查询呢?

二、查询可能会执行三种操作

  • 检索元素的子集以生成新序列,而不修改各个元素。 查询然后可能以各种方式对返回的序列进行排序或分组,如下面的示例所示(假定 scores 是 int[]):

IEnumerable<int> highScoresQuery = from score in scores where score > 80 orderby score descending select score;

  • 如前面的示例所示检索元素的序列,但是将它们转换为新类型的对象。 例如,查询可以只从数据源中的某些客户记录检索姓氏。或者可以检索完整记录,然后用于构造其他内存中对象类型甚至是 XML 数据,再生成最终的结果序列。 下面的示例演示从 int到 string 的投影。 请注意 highScoresQuery 的新类型。
IEnumerable<string> highScoresQuery2 =from score in scoreswhere score > 80orderby score descendingselect $"The score is {score}";

  • 检索有关源数据的单独值,如:
  • 与特定条件匹配的元素数。

  • 具有最大或最小值的元素。

  • 与某个条件匹配的第一个元素,或指定元素集中特定值的总和。 例如,下面的查询从 scores 整数数组返回大于 80 的分数的数量:

int highScoreCount =(from score in scoreswhere score > 80select score).Count();

在前面的示例中,请注意在调用 Count 方法之前,在查询表达式两边使用了括号。 也可以通过使用新变量存储具体结果,来表示此行为。 这种方法更具可读性,因为它使存储查询的变量与存储结果的查询分开。

IEnumerable<int> highScoresQuery3 =from score in scoreswhere score > 80select score;int scoreCount = highScoresQuery3.Count();

三、查询表达式

查询表达式必须以 from 子句开头,且必须以 select 或 group 子句结尾。在第一个 from 子句与最后一个 select 或 group 子句之间,可以包含以下这些可选子句中的一个或多个:where、orderby、join、let,甚至是其他 from 子句。 还可以使用 into 关键字,使 join 或 group 子句的结果可以充当相同查询表达式中的其他查询子句的源。

下面的代码示例演示一个简单查询表达式,它具有一个数据源、一个筛选子句、一个排序子句并且不转换源元素。 该查询以 select子句结尾。

static void Main()
{// Data source.int[] scores = { 90, 71, 82, 93, 75, 82 };// Query Expression.IEnumerable<int> scoreQuery = //query variablefrom score in scores //requiredwhere score > 80 // optionalorderby score descending // optionalselect score; //must end with select or group// Execute the query to produce the resultsforeach (int testScore in scoreQuery){Console.WriteLine(testScore);}
}
// Outputs: 93 90 82 82

查询变量

在上面的示例中,scoreQuery 是查询变量,它有时仅仅称为查询。查询变量可以存储采用查询语法、方法语法或是两者的组合进行表示的查询,而不是查询的结果。

开始查询表达式

查询表达式必须以 from 子句开头。 它指定数据源以及范围变量。 范围变量表示遍历源序列时,源序列中的每个连续元素。 范围变量基于数据源中元素的类型进行强类型化。 在下面的示例中,因为 countries 是 Country 对象的数组,所以范围变量也类型化为 Country。 因为范围变量是强类型,所以可以使用点运算符访问该类型的任何可用成员。

IEnumerable<Country> countryAreaQuery =from country in countrieswhere country.Area > 500000 //sq kmselect country;

范围变量一直处于范围中,直到查询使用分号或 continuation 子句退出。

查询表达式可能会包含多个 from 子句。 在源序列中的每个元素本身是集合或包含集合时,可使用其他 from 子句。 例如,假设具有 Country 对象的集合,其中每个对象都包含名为 Cities 的 City 对象集合。 若要查询每个 Country 中的 City 对象,请使用两个 from 子句,如下所示:

IEnumerable<City> cityQuery =from country in countriesfrom city in country.Citieswhere city.Population > 10000select city;

结束查询表达式

查询表达式必须以 group 子句或 select 子句结尾。

group 子句

使用 group 子句可生成按指定键组织的组的序列。 键可以是任何数据类型。 例如,下面的查询会创建包含一个或多个 Country 对象并且其键是 char 值的组的序列。

var queryCountryGroups =from country in countriesgroup country by country.Name[0];

select 子句

使用 select 子句可生成所有其他类型的序列。 简单 select 子句只生成类型与数据源中包含的对象相同的对象的序列。 在此示例中,数据源包含 Country 对象。 orderby 子句只按新顺序对元素进行排序,而 select 子句生成重新排序的 Country 对象的序列。

IEnumerable<Country> sortedQuery =from country in countriesorderby country.Areaselect country;

select 子句可以用于将源数据转换为新类型的序列。 此转换也称为投影。 在下面的示例中,select 子句对只包含原始元素中的字段子集的匿名类型序列进行投影。 请注意,新对象使用对象初始值设定项进行初始化。

// Here var is required because the query
// produces an anonymous type.
var queryNameAndPop =from country in countriesselect new { Name = country.Name, Pop = country.Population };

使用“into”进行延续

可以在 select 或 group 子句中使用 into 关键字创建存储查询的临时标识符。 如果在分组或选择操作之后必须对查询执行其他查询操作,则可以这样做。 在下面的示例中,countries 按 1000 万范围,根据人口进行分组。 创建这些组之后,附加子句会筛选出一些组,然后按升序对组进行排序。 若要执行这些附加操作,需要由 countryGroup 表示的延续。

// percentileQuery is an IEnumerable<IGrouping<int, Country>>
var percentileQuery =from country in countrieslet percentile = (int) country.Population / 10_000_000group country by percentile into countryGroupwhere countryGroup.Key >= 20orderby countryGroup.Keyselect countryGroup;// grouping is an IGrouping<int, Country>
foreach (var grouping in percentileQuery)
{Console.WriteLine(grouping.Key);foreach (var country in grouping)Console.WriteLine(country.Name + ":" + country.Population);
}

筛选、排序和联接

在开头 from 子句与结尾 select 或 group 子句之间,所有其他子句(wherejoinorderbyfromlet)都是可选的。任何可选子句都可以在查询正文中使用零次或多次。

where 子句

使用 where 子句可基于一个或多个谓词表达式,从源数据中筛选出元素。 以下示例中的 where 子句具有一个谓词及两个条件。

IEnumerable<City> queryCityPop =from city in citieswhere city.Population < 200000 && city.Population > 100000select city;

orderby 子句

使用 orderby 子句可按升序或降序对结果进行排序。 还可以指定次要排序顺序。 下面的示例使用 Area 属性对 country 对象执行主要排序。 然后使用 Population 属性执行次要排序。

IEnumerable<Country> querySortedCountries =from country in countriesorderby country.Area, country.Population descendingselect country;

ascending 关键字是可选的;如果未指定任何顺序,则它是默认排序顺序。

join 子句

使用 join 子句可基于每个元素中指定的键之间的相等比较,将一个数据源中的元素与另一个数据源中的元素进行关联和/或合并。在 LINQ 中,联接操作是对元素属于不同类型的对象序列执行。 联接了两个序列之后,必须使用 select 或 group 语句指定要存储在输出序列中的元素。 还可以使用匿名类型将每组关联元素中的属性合并到输出序列的新类型中。 下面的示例关联其 Category 属性与 categories 字符串数组中一个类别匹配的 prod 对象。 筛选出其 Category 不与 categories 中的任何字符串匹配的产品。select 语句会投影其属性取自 cat 和 prod 的新类型。

var categoryQuery =from cat in categoriesjoin prod in products on cat equals prod.Categoryselect new { Category = cat, Name = prod.Name };

还可以通过使用 into 关键字将 join 操作的结果存储到临时变量中来执行分组联接。

let 子句

使用 let 子句可将表达式(如方法调用)的结果存储在新范围变量中。 在下面的示例中,范围变量 firstName 存储 Split 返回的字符串数组的第一个元素。

string[] names = { "Svetlana Omelchenko", "Claire O'Donnell", "Sven Mortensen", "Cesar Garcia" };
IEnumerable<string> queryFirstNames =from name in nameslet firstName = name.Split(' ')[0]select firstName;foreach (string s in queryFirstNames)Console.Write(s + " ");
//Output: Svetlana Claire Sven Cesar

查询表达式中的子查询

查询子句本身可能包含查询表达式,这有时称为子查询。 每个子查询都以自己的 from 子句开头,该子句不一定指向第一个 from子句中的相同数据源。 例如,下面的查询演示在 select 语句用于检索分组操作结果的查询表达式。

var queryGroupMax =from student in studentsgroup student by student.GradeLevel into studentGroupselect new{Level = studentGroup.Key,HighestScore =(from student2 in studentGroupselect student2.Scores.Average()).Max()};

转载于:https://www.cnblogs.com/wangyihome/p/10341000.html

LINQ-查询表达式基础相关推荐

  1. LINQ查询表达式基础

    LINQ,语言集成查询(Language Integrated Query)是一组用C#和Visual Basic语言的扩展. 对于编写查询的开发人员来说,LINQ 最明显的"语言集成&qu ...

  2. LINQ 查询表达式(C# 编程指南)

    LINQ 查询表达式(C# 编程指南) 语言集成查询 (LINQ) 是一组技术的名称,这些技术建立在将查询功能直接集成到 C# 语言(以及 Visual Basic 和可能的任何其他 .NET 语言) ...

  3. [深入学习C#]LINQ查询表达式详解(1)——基本语法、使用扩展方法和Lambda表达式简化LINQ查询

    此文章非原创,转载自诗人江湖老,原文地址 在Git上下载源码 在工程中我们少不了要定义类或者结构去储存数据,这些数据将被临时地储存在内存中,现在我们想要对其完成一些类似于查找.过滤等等常见的任务的时候 ...

  4. 「C#」LinQ查询表达式

    关于LinQ查询表达式 语言集成查询 (LINQ) 是一系列直接将查询功能集成到 C# 语言的技术统称. LINQ 通过提供处理各种数据源和数据格式的数据的一致模型,简化了每种数据源或数据格式再查询时 ...

  5. LINQ之路 5:LINQ查询表达式

    书写LINQ查询时又两种语法可供选择:方法语法(Fluent Syntax)和查询表达式(Query Expression). LINQ方法语法的本质是通过扩展方法和Lambda表达式来创建查询.C# ...

  6. [深入学习C#]LINQ查询表达式详解(2)——查询表达式的转换

    转载自诗人江湖老,原文地址 C#在执行LINQ查询表达式的时候,并不会指定其执行语义,而是将查询表达式转换为遵循查询表达式模式的方法的调用.具体而言,查询表达式将转换为以下名称的调用:Where.Se ...

  7. LINQ查询表达式和LAMBDA点标记方法基础

    在上一篇文章中,我们介绍了LINQ的一些基本用法,这一篇我们来看下另一种更简洁更优雅的表达式,Lambda表达式,也可以叫做点标记方法. 相信大家在实际工作中都用到过这两种方式,下面我们还是用实例来看 ...

  8. C#中其他简单LINQ查询表达式的简单使用介绍

    本文主要记录下其他简单LINQ表达式,因为比较简单,记录下以后方便回忆,本文也会持续更新. 一些有用的LINQ扩展方法: LINQ表达式 作用 是否延迟查询 Range 生成指定范围内的整数的序列   ...

  9. 查询表达式和LINQ to Objects

    查询表达式实际上是由编译器"预处理"为"普通"的C#代码,接着以完全普通的方式进行编译.这种巧妙的发式将查询集合到了语言中,而无须把语义改得乱七八糟 LINQ的 ...

  10. php mql获取结果集,promql查询表达式

    Basics 即时矢量选择器 =:匹配与标签相等的内容 !=:不匹配与标签相等的内容 =~: 根据正则表达式匹配与标签符合的内容 !~:根据正则表达式不匹配与标签符合的内容 示例: http_requ ...

最新文章

  1. nginx+passenger下504 Gateway-Timeout问题的解决办法
  2. 201671010460朱艺璇 实验三作业互评与改进报告
  3. spark sql 性能优化
  4. 在SQL Server Management Studio 中建立外键约束
  5. [bzoj1086][SCOI2005]王室联邦
  6. system.js 替换 require.js
  7. javascript数据结构之队列
  8. python有趣的简单代码-盘点10个一行强大的、有趣的Python源代码
  9. 中国数字音乐——版权问题之公司分析
  10. 真实业务订单 拆单 架构与实战
  11. beanshell学习
  12. zemax中如何和matlab中通信,如何在Zemax与Matlab间通信
  13. 知乎企业认证怎么弄?知乎企业号怎么申请?详解来了
  14. TPshop项目介绍
  15. 赛效:Xmind思维导图怎么删除子主题
  16. java过滤ios表情,JS前端去掉emoji表情和Java后台处理emoji表情方法
  17. java使用knn实现mnist_java使用knn实现mnist - 百度学术
  18. 网上搜索电子书的办法
  19. EI漏录的会议文章,如何申请EI数据库补录!
  20. JAVAEE学习day02

热门文章

  1. java jxl label_jxl.write.label
  2. matlab打包多个m文件,MATLAB GUI多个m文件和fig如何生成exe文件
  3. php if k 1,PHP实现大数字格式化成K/M/B结尾的简短形式
  4. (转)Uncaught TypeError: Cannot set property 'innerHTML' of null
  5. DBVisualizer 添加数据库JDBC驱动
  6. 信息图形化探索:图形化简历
  7. 折线图_R语言画折线图?
  8. java.lang.classnotfo_java.lang.ClassNotFoundException
  9. 前景检测算法(二)--codebook和平均背景法
  10. 2022年考研数据结构_5 树