ZetCode

C# LINQ 查询表达式

最后修改于 2023 年 7 月 5 日

C# LINQ 查询表达式教程展示了如何使用查询在 C# 中提取和转换数据。

语言集成查询 (LINQ) 是一组基于将查询功能直接集成到 C# 语言中的技术。

查询是一组指令,描述了从给定数据源(或多个数据源)检索哪些数据,以及返回的数据应该具有什么形状和组织结构。 LINQ 查询表达式可用于方便地从数组、可枚举类、XML 文档、关系数据库和第三方数据源中提取和处理数据。

查询表达式可用于查询和转换来自任何启用 LINQ 的数据源的数据。 查询表达式具有延迟执行的特性。 它们只有在我们迭代查询变量时才会被执行,例如在 foreach 语句中。

C# 查询表达式过滤器

在接下来的示例中,我们将展示如何过滤数据。

Program.cs
int[] vals = { -2, 4, 6, -1, 2, 0, 1, -3, -4, 2, 3, 8 };

var pos = 
    from val in vals 
    where val > 0
    select val;

Console.WriteLine(string.Join(" ", pos));

var evens = 
    from val in vals
    where val % 2 == 0
    select val;

Console.WriteLine(string.Join(" ", evens));

在该示例中,我们从数组中过滤掉正值和偶数值。

var pos = 
    from val in vals 
    where val > 0
    select val;

使用 from 子句,我们遍历数组的元素。 这些元素使用 where 进行过滤,最后使用 select 进行投影。

$ dotnet run 
4 6 2 1 2 3 8
-2 4 6 2 0 -4 2 8

接下来,我们使用 || 运算符组合条件。

Program.cs
var words = new List<string> { "sky", "bee", "forest", "new", "falcon", "rock",
        "cloud", "war", "small", "eagle", "blue", "frost", "water" };

var found = 
    from word in words
    where word.StartsWith("f") || word.StartsWith("w")
    select word;

foreach (var word in found)
{
    Console.WriteLine(word);
}

我们在 where 子句中应用两个条件。 我们获取以 'f' 或 'w' 开头的单词。

$ dotnet run
forest
falcon
war
frost
water

在下面的示例中,我们使用 && 应用两个条件。

Program.cs
var cars = new List<Car>
{
    new ("Audi", 52642),
    new ("Mercedes", 57127),
    new ("Skoda", 9000),
    new ("Volvo", 29000),
    new ("Bentley", 350000),
    new ("Citroen", 21000),
    new ("Hummer", 41400),
    new ("Volkswagen", 21600)
};

var res = from car in cars
          where car.Price > 30000 && car.Price < 100000
          select new { car.Name, car.Price };

foreach (var car in res)
{
    Console.WriteLine($"{car.Name} {car.Price}");
}

record Car(string Name, int Price);

在该示例中,我们使用 where 子句过滤汽车对象列表。 我们包括所有价格在 30000 到 100000 之间的汽车。

$ dotnet run
Audi 52642
Mercedes 57127
Hummer 41400

C# 查询 first/last

我们使用 FirstLast 方法获取可枚举对象的第一个和最后一个元素。

Program.cs
string[] words = { "falcon", "oak", "sky", "cloud", "tree", "tea", "water" };

var first = (from word in words
        where word.Length == 3
        select word).First();

Console.WriteLine(first);

var last = (from word in words
        where word.Length == 3
        select word).Last();

Console.WriteLine(last);

在该示例中,我们访问数组的元素。

var first = (from word in words
    where word.Length == 3
    select word).First();

我们获取长度为 3 的第一个元素。

var last = (from word in words
    where word.Length == 3
    select word).Last();

我们检索长度为 3 的最后一个元素。

$ dotnet run
oak
tea

C# 查询 select

select 子句将序列的每个元素投影成一种新的形式。 它选择、投影和转换集合中的元素。 在其他语言中,select 通常被称为 Map。

Program.cs
int[] vals = { 2, 4, 6, 8 };

var powered = 
    from val in vals 
    select Math.Pow(val, 2);

Console.WriteLine(string.Join(", ", powered));

string[] words = { "sky", "earth", "oak", "falcon" };
var wordLens = 
    from word in words
    select word.Length;

Console.WriteLine(string.Join(", ", wordLens));

在该示例中,我们将整数数组转换为其幂的序列,并将单词数组转换为单词长度的序列。

$ dotnet run
4, 16, 36, 64
3, 5, 3, 6

C# 查询 select into 匿名类型

投影是从返回的对象中选择特定的字段。 投影是通过 select 子句执行的。 我们可以将字段投影到匿名类型中。

Program.cs
User[] users =
{
  new (1, "John", "London", "2001-04-01"),
  new (2, "Lenny", "New York", "1997-12-11"),
  new (3, "Andrew", "Boston", "1987-02-22"),
  new (4, "Peter", "Prague", "1936-03-24"),
  new (5, "Anna", "Bratislava", "1973-11-18"),
  new (6, "Albert", "Bratislava", "1940-12-11"),
  new (7, "Adam", "Trnava", "1983-12-01"),
  new (8, "Robert", "Bratislava", "1935-05-15"),
  new (9, "Robert", "Prague", "1998-03-14"),
};

var res = from user in users
          where user.City == "Bratislava"
          select new { user.Name, user.City };

Console.WriteLine(string.Join(", ", res));

record User(int id, string Name, string City, string DateOfBirth);

在该示例中,我们选择居住在布拉迪斯拉发的用户。

var res = from user in users
          where user.City == "Bratislava"
          select new { user.Name, user.City };

使用 select new 子句,我们创建一个具有两个字段的匿名类型:NameCity

$ dotnet run
{ Name = Anna, City = Bratislava }, { Name = Albert, City = Bratislava },
{ Name = Robert, City = Bratislava }

C# 查询扁平化数组

以下示例将数组的数组扁平化为单个数组。

Program.cs
int[][] vals = {
    new[] {1, 2, 3},
    new[] {4},
    new[] {5, 6, 6, 2, 7, 8},
};

var res = (from nested in vals
           from e in nested
           select e);

Console.WriteLine(string.Join(", ", res));

要扁平化数组,我们使用两个 from 子句。

$ dotnet run
1, 2, 2, 3, 4, 5, 6, 6, 7, 8

C# 查询 Concat

Concat 方法连接两个序列。

Program.cs
User[] users1 = 
{
    new ("John", "Doe", "gardener"),
    new ("Jane", "Doe", "teacher"), 
    new ("Roger", "Roe", "driver"),
};

User[] users2 = 
{
    new ("Peter", "Smith", "teacher"),
    new ("Lucia", "Black", "accountant"), 
    new ("Michael", "Novak", "programmer"),
};

var users = (from u1 in users1 select u1).Concat(from u2 in users2 select u2);

foreach (var user in users)
{
    Console.WriteLine(user);
}

record User(string FirstName, string LastName, string Occupation);

我们有两个用户数组。 我们使用 Concat 将它们合并。

$ dotnet run
User { FirstName = John, LastName = Doe, Occupation = gardener }
User { FirstName = Jane, LastName = Doe, Occupation = teacher }
User { FirstName = Roger, LastName = Roe, Occupation = driver }
User { FirstName = Peter, LastName = Smith, Occupation = teacher }
User { FirstName = Lucia, LastName = Black, Occupation = accountant }
User { FirstName = Michael, LastName = Novak, Occupation = programmer }

C# 查询笛卡尔积

笛卡尔积是两个集合的乘积,形成所有有序对的集合。

Program.cs
char[] letters = "abcdefghi".ToCharArray();
char[] digits = "123456789".ToCharArray();
 
var coords =
    from l in letters
    from d in digits
    select $"{l}{d}";
 
foreach (var coord in coords)
{
    Console.Write($"{coord} ");

    if (coord.EndsWith("9"))
    {
        Console.WriteLine();
    }
}

Console.WriteLine();

在该示例中,我们创建字母和数字的笛卡尔积。

var coords =
    from l in letters
    from d in digits
    select $"{l}{d}";

为了完成这项任务,我们使用两个 from 子句。

$ dotnet run
a1 a2 a3 a4 a5 a6 a7 a8 a9 
b1 b2 b3 b4 b5 b6 b7 b8 b9 
c1 c2 c3 c4 c5 c6 c7 c8 c9 
d1 d2 d3 d4 d5 d6 d7 d8 d9 
e1 e2 e3 e4 e5 e6 e7 e8 e9 
f1 f2 f3 f4 f5 f6 f7 f8 f9 
g1 g2 g3 g4 g5 g6 g7 g8 g9 
h1 h2 h3 h4 h5 h6 h7 h8 h9 
i1 i2 i3 i4 i5 i6 i7 i8 i9 

C# 查询 Count & Sum

Count 返回序列中元素的数量。 Sum 计算数值序列的总和。

Program.cs
var content =
    @"Foxes are omnivorous mammals belonging to several genera
of the family Canidae. Foxes have a flattened skull, upright triangular ears,
a pointed, slightly upturned snout, and a long bushy tail. Foxes live on every
continent except Antarctica. By far the most common and widespread species of
fox is the red fox.";

var lines = content.Split("\n");

var n1 = (from line in lines
          select line).Count();

Console.WriteLine($"There are {n1} lines");

var words = content.Split(" ");

var n2 = (from word in words
          select word).Count();

Console.WriteLine($"There are {n2} words");

var chars = content.ToCharArray();

var n3 = (from c in chars
          where c == 'f'
          select c).Count();

Console.WriteLine($"There are {n3} f letters");

在该示例中,我们使用 Count 方法来计算文本中的行数、单词数和 'f' 字符数。

$ dotnet run
There are 5 lines
There are 47 words
There are 7 f letters

在下一个示例中,我们使用 Sum 方法。

Program.cs
var vals = new List<int> { 1, -2, 3, -4, 5, 6, 7, -8 };
var s = (from x in vals where x > 0 select x).Sum();

Console.WriteLine($"The sum of positive values is: {s}");

var words = new List<string> { "falcon", "eagle", "hawk", "owl" };
int len = (from x in words select x.Length).Sum();

Console.WriteLine($"There are {len} letters in the list");

在该示例中,我们计算 vals 列表中正值的数量以及 words 列表中字符的数量。

$ dotnet run
The sum of positive values is: 22
There are 18 letters in the list

C# 查询 orderby

使用 OrderBy 方法或 orderby 子句,我们可以对序列的元素进行排序。

Program.cs
int[] vals = { 4, 5, 3, 2, 7, 0, 1, 6 };

var result = from e in vals
             orderby e ascending
             select e;

Console.WriteLine(string.Join(", ", result));

var result2 = from e in vals
              orderby e descending
              select e;

Console.WriteLine(string.Join(", ", result2));

在该示例中,我们按升序和降序对整数进行排序。 ascending 关键字是可选的。

$ dotnet run
0, 1, 2, 3, 4, 5, 6, 7
7, 6, 5, 4, 3, 2, 1, 0

在下一个示例中,我们按多个字段对对象进行排序。

Program.cs
var users = new List<User>
{
    new ("Robert", "Novak", 1770),
    new ("John", "Doe", 1230),
    new ("Lucy", "Novak", 670),
    new ("Ben", "Walter", 2050),
    new ("Robin", "Brown", 2300),
    new ("Amy", "Doe", 1250),
    new ("Joe", "Draker", 1190),
    new ("Janet", "Doe", 980),
    new ("Peter", "Novak", 990),
    new ("Albert", "Novak", 1930),
};

Console.WriteLine("sort descending by last name and salary");

var sortedUsers = from user in users
                  orderby user.LastName descending, user.Salary descending
                  select user;

foreach (var user in sortedUsers)
{
    Console.WriteLine(user);
}

Console.WriteLine("-------------------------");

Console.WriteLine("sort ascending by last name and salary");

var sortedUsers2 = from user in users
                   orderby user.LastName ascending, user.Salary ascending
                   select user;

foreach (var user in sortedUsers2)
{
    Console.WriteLine(user);
}

record User(string FirstName, string LastName, int Salary);

在该示例中,首先按用户的姓氏,然后按他们的工资对用户进行排序。

var sortedUsers = from user in users
    orderby user.LastName descending, user.Salary descending
    select user;

在这里,我们按用户的姓氏,然后按他们的薪水进行降序排序。

var sortedUsers2 = from user in users
    orderby user.LastName ascending, user.Salary ascending
    select user;

在这里,我们按用户的姓氏排序,然后按工资升序排序。

$ dotnet run
sort descending by last name and salary
User { FirstName = Ben, LastName = Walter, Salary = 2050 }
User { FirstName = Albert, LastName = Novak, Salary = 1930 }
User { FirstName = Robert, LastName = Novak, Salary = 1770 }
User { FirstName = Peter, LastName = Novak, Salary = 990 }
User { FirstName = Lucy, LastName = Novak, Salary = 670 }
User { FirstName = Joe, LastName = Draker, Salary = 1190 }
User { FirstName = Amy, LastName = Doe, Salary = 1250 }
User { FirstName = John, LastName = Doe, Salary = 1230 }
User { FirstName = Janet, LastName = Doe, Salary = 980 }
User { FirstName = Robin, LastName = Brown, Salary = 2300 }
-------------------------
sort ascending by last name and salary
User { FirstName = Robin, LastName = Brown, Salary = 2300 }
User { FirstName = Janet, LastName = Doe, Salary = 980 }
User { FirstName = John, LastName = Doe, Salary = 1230 }
User { FirstName = Amy, LastName = Doe, Salary = 1250 }
User { FirstName = Joe, LastName = Draker, Salary = 1190 }
User { FirstName = Lucy, LastName = Novak, Salary = 670 }
User { FirstName = Peter, LastName = Novak, Salary = 990 }
User { FirstName = Robert, LastName = Novak, Salary = 1770 }
User { FirstName = Albert, LastName = Novak, Salary = 1930 }
User { FirstName = Ben, LastName = Walter, Salary = 2050 }

C# 查询 Reverse

Reverse 方法反转序列中元素的顺序。(请注意,这与按降序排序不同。)

Program.cs
int[] vals = { 1, 3, 6, 0, -1, 2, 9, 9, 8 };

var reversed = (from val in vals select val).Reverse();
Console.WriteLine(string.Join(", ", reversed));

在该示例中,我们使用方法和查询语法反转数组的元素。

$ dotnet run
8, 9, 9, 2, -1, 0, 6, 3, 1

C# LINQ group by

我们可以根据某个键将数据分组到不同的类别中。

Program.cs
var cars = new List<Car>
{
    new ("Audi", "red", 52642),
    new ("Mercedes", "blue", 57127),
    new ("Skoda", "black", 9000),
    new ("Volvo", "red", 29000),
    new ("Bentley", "yellow", 350000),
    new ("Citroen", "white", 21000),
    new ("Hummer", "black", 41400),
    new ("Volkswagen", "white", 21600),
};

var groups = from car in cars
             group car by car.Colour;

foreach (var group in groups)
{
    Console.WriteLine(group.Key);

    foreach (var car in group)
    {
        Console.WriteLine($" {car.Name} {car.Price}");
    }
}

record Car(string Name, string Colour, int Price);

在该示例中,我们将可用的汽车按颜色分组。

$ dotnet run
red
  Audi 52642
  Volvo 29000
blue
  Mercedes 57127
black
  Skoda 9000
  Hummer 41400
yellow
  Bentley 350000
white
  Citroen 21000
  Volkswagen 21600

在下面的示例中,我们执行分组和聚合操作。

Program.cs
Revenue[] revenues = 
{
    new (1, "Q1", 2340),
    new (2, "Q1", 1200),
    new (3, "Q1", 980),
    new (4, "Q2", 340),
    new (5, "Q2", 780),
    new (6, "Q3", 2010),
    new (7, "Q3", 3370),
    new (8, "Q4", 540),
};

var res = from revenue in revenues
          group revenue by revenue.Quarter
          into g
          select new { Quarter = g.Key, Total = g.Sum(e => e.Amount) };

foreach (var line in res)
{
    Console.WriteLine(line);
}

record Revenue(int Id, string Quarter, int Amount);

我们有四个季度的收入。我们按季度对收入进行分组,并对金额求和。

$ dotnet run
{ Quarter = Q1, Total = 4520 }
{ Quarter = Q2, Total = 1120 }
{ Quarter = Q3, Total = 5380 }
{ Quarter = Q4, Total = 540 }

我们可以使用 where 子句对聚合后的数据应用筛选器。

Program.cs
Revenue[] revenues = 
{
    new (1, "Q1", 2340),
    new (2, "Q1", 1200),
    new (3, "Q1", 980),
    new (4, "Q2", 340),
    new (5, "Q2", 780),
    new (6, "Q3", 2010),
    new (7, "Q3", 3370),
    new (8, "Q4", 540),
};

var res = from revenue in revenues
          group revenue by revenue.Quarter
          into g
          where g.Count() == 2
          select new { Quarter = g.Key, Total = g.Sum(c => c.Amount) };


foreach (var line in res)
{
    Console.WriteLine(line);
}

record Revenue(int Id, string Quarter, int Amount);

在此示例中,我们只选择那些恰好有两条收入记录的季度。

$ dotnet run
{ Quarter = Q2, Total = 1120 }
{ Quarter = Q3, Total = 5380 }

C# LINQ 词频统计

在下一个示例中,我们统计文件中单词的频率。

$ wget https://raw.githubusercontent.com/janbodnar/data/main/the-king-james-bible.txt

我们使用《英王钦定本圣经》。

Program.cs
using System.Text.RegularExpressions;

var fileName = "the-king-james-bible.txt";
var text = File.ReadAllText(fileName);

var dig = new Regex(@"\d");
var matches = new Regex("[a-z-A-Z']+").Matches(text);

var words = 
    from match in matches
        let val = match.Value
        where !dig.IsMatch(val)
    select match.Value;

var topTen =
    (from word in words
        group word by word into wg
        orderby wg.Count() descending
        select new {word = wg.Key, Total = wg.Count()}
    ).Take(10);

foreach (var e in topTen)
{
    Console.WriteLine($"{e.word}: {e.Total}");
}

我们统计《英王钦定本圣经》中单词的频率。

var matches = new Regex("[a-z-A-Z']+").Matches(text);
var words = matches.Select(m => m.Value).ToList();

我们使用 Matches 方法找到所有匹配项。从匹配集合中,我们将所有单词放入一个列表中。

var words = 
from match in matches
    let val = match.Value
    where !dig.IsMatch(val)
select match.Value;

在第一个查询中,我们找到所有匹配项。 从匹配集合中,我们得到所有单词。

var topTen =
    (from word in words
        group word by word into wg
        orderby wg.Count() descending
        select new {word = wg.Key, Total = wg.Count()}
    ).Take(10);

这些单词按频率降序分组和排序。 我们选取最常见的十个单词。

$ dotnet run
the 62103
and 38848
of 34478
to 13400
And 12846
that 12576
in 12331
shall 9760
he 9665
unto 8942

C# LINQ join

join 子句连接序列。

Program.cs
string[] basketA = { "coin", "book", "fork", "cord", "needle" };
string[] basketB = { "watches", "coin", "pen", "book", "pencil" };

var res = from item1 in basketA
          join item2 in basketB
          on item1 equals item2
          select item1;

foreach (var item in res)
{
    Console.WriteLine(item);
}

在该示例中,我们有两个数组。 使用 join 子句,我们找到两个数组中都存在的项目。

$ dotnet run
coin
book

硬币和书籍单词包含在两个数组中。

C# 查询转换

我们可以将返回的可枚举对象转换为列表、数组或字典。

Program.cs
User[] users =
{
  new (1, "John", "London", "2001-04-01"),
  new (2, "Lenny", "New York", "1997-12-11"),
  new (3, "Andrew", "Boston", "1987-02-22"),
  new (4, "Peter", "Prague", "1936-03-24"),
  new (5, "Anna", "Bratislava", "1973-11-18"),
  new (6, "Albert", "Bratislava", "1940-12-11"),
  new (7, "Adam", "Trnava", "1983-12-01"),
  new (8, "Robert", "Bratislava", "1935-05-15"),
  new (9, "Robert", "Prague", "1998-03-14"),
};

string[] cities = (from user in users
                   select user.City).Distinct().ToArray();

Console.WriteLine(string.Join(", ", cities));

Console.WriteLine("------------");

List<User> inBratislava = (from user in users
                                 where user.City == "Bratislava"
                                 select user).ToList();

foreach (var user in inBratislava)
{
    Console.WriteLine(user);
}

Console.WriteLine("------------");

Dictionary<int, string> userIds =
        (from user in users
         select user).ToDictionary(user => user.id, user => user.Name);

foreach (var kvp in userIds)
{
    Console.WriteLine($"{kvp.Key}: {kvp.Value}");
}

record User(int id, string Name, string City, string DateOfBirth);

我们对数据源执行三个查询; 生成的可枚举对象被转换为列表、数组和字典。

string[] cities = (from user in users
                   select user.City).Distinct().ToArray();

在此查询中,我们从数据源中选择所有城市。 我们应用 Distinct 方法,最后调用 ToArray 方法。

List<User> inBratislava = (from user in users
                                 where user.City == "Bratislava"
                                 select user).ToList();

在这里,我们获得居住在布拉迪斯拉发的用户的列表; 我们调用 ToList 方法。

Dictionary<int, string> userIds =
        (from user in users
         select user).ToDictionary(user => user.id, user => user.Name);

在此查询中,我们将用户名及其 ID 转换为字典。

$ dotnet run
London, New York, Boston, Prague, Bratislava, Trnava
------------
User { id = 5, Name = Anna, City = Bratislava, DateOfBirth = 1973-11-18 }
User { id = 6, Name = Albert, City = Bratislava, DateOfBirth = 1940-12-11 }
User { id = 8, Name = Robert, City = Bratislava, DateOfBirth = 1935-05-15 }
------------
1: John
2: Lenny
3: Andrew
4: Peter
5: Anna
6: Albert
7: Adam
8: Robert
9: Robert

C# 查询 XML

LINQ 可用于处理 XML。

Program.cs
using System.Xml.Linq;

string myXML = @"
<Users>
    <User>
        <Name>Jack Moore</Name>
        <Occupation>programmer</Occupation>
    </User>
    <User>
        <Name>Paul Novak</Name>
        <Occupation>driver</Occupation>
    </User>
    <User>
        <Name>Frank Woody</Name>
        <Occupation>teacher</Occupation>
    </User>
    <User>
        <Name>Martina Doe</Name>
        <Occupation>programmer</Occupation>
    </User>
    <User>
        <Name>Lucia Black</Name>
        <Occupation>teacher</Occupation>
    </User>
</Users>";

var xdoc = new XDocument();
xdoc = XDocument.Parse(myXML);

var data = from u in xdoc.Root.Descendants()
              where (string)u.Element("Occupation") == "teacher"
              select u.Element("Name");

foreach (var e in data)
{
    Console.WriteLine($"{e}");
}

我们解析 XML 数据并选择所有女性姓名。

$ dotnet run
<Name>Frank Woody</Name>
<Name>Lucia Black</Name>

C# 查询列出目录内容

Directory.EnumerateFiles 返回满足指定条件的完整文件名的可枚举集合。

Program.cs
var path = "/home/user2/";

var files = from file in Directory.EnumerateFiles(path, "*.txt",
                SearchOption.AllDirectories)
            where Path.GetFileName(file).ToLower().Contains("data")
            select file;

foreach (var file in files)
{
    Console.WriteLine("{0}", file);
}

Console.WriteLine("{0} files found.", files.Count<string>().ToString());

该示例递归搜索所有名称包含单词 data 的文本文件。

C# 查询 let 子句

let 子句允许我们存储子表达式的结果,以便在后续子句中使用它。

data.csv
John Doe, gardener, 12/5/1997
Jane Doe, teacher, 5/16/1983
Robert Smith, driver, 4/2/2001
Maria Smith, cook, 9/21/1976

这些是 data.csv 文件的内容。

Program.cs
using System.Text;

var path = "data.csv";
var lines = File.ReadLines(path, Encoding.UTF8);

var users = from line in lines
            let fields = line.Replace(", ", ",").Split(",")
            select new User(fields[0], fields[1], DateTime.Parse(fields[2]));

var sorted = from user in users
             orderby user.DateOfBirth descending
             select user;

foreach (var user in sorted)
{
    Console.WriteLine(user);
}

public record User(string Name, string Occupation, DateTime DateOfBirth);

在该示例中,我们解析 data.csv 文件并创建一个用户序列; 这些用户按出生日期降序排序。

var users = from line in lines
    let fields = line.Replace(", ", ",").Split(",")
    select new User(fields[0], fields[1], DateTime.Parse(fields[2]));

在第一个查询表达式中,我们将一行拆分为其字段; 这些字段存储在 fields 变量中,该变量稍后在 select 子句中使用。

$ dotnet run
User { Name = Robert Smith, Occupation = driver, DateOfBirth = 4/2/2001 12:00:00 AM }
User { Name = John Doe, Occupation = gardener, DateOfBirth = 12/5/1997 12:00:00 AM }
User { Name = Jane Doe, Occupation = teacher, DateOfBirth = 5/16/1983 12:00:00 AM }
User { Name = Maria Smith, Occupation = cook, DateOfBirth = 9/21/1976 12:00:00 AM }

在本文中,我们使用了 C# 中的 LINQ 查询表达式。

来源

查询表达式基础知识

作者

我的名字是 Jan Bodnar,我是一位热情的程序员,拥有丰富的编程经验。 自 2007 年以来,我一直在撰写编程文章。 迄今为止,我已经撰写了超过 1,400 篇文章和 8 本电子书。 我拥有超过十年的编程教学经验。

列出所有 C# 教程