【问题标题】:DataTable AsEnumerable matching a single valueDataTable AsEnumerable 匹配单个值
【发布时间】:2018-01-10 20:08:42
【问题描述】:

假设我的查询返回一个 DataTable,它是一个电子邮件地址列表,一个名为“email”的 varchar 列;这些电子邮件被授权做某事。

jane@doe.com
mike@foo.com
donald@duck.com

当前登录的用户是harry@houdini.com。他没有被授权。他不在名单上

是否可以使用 Linq 迭代 DataRows 并返回布尔值 false

或者返回一个nullNothing或空的对象?

本质上,我想知道Linq版本的

 Authorized = List.Contains( "harry@houdini.com")

我真的很想知道如何在 C# 和 VB 中做到这一点。

谢谢

【问题讨论】:

  • 使用Any() 方法检查是否有任何项目与您的谓词匹配。
  • 您展示的代码解决该问题的有效 LINQ 解决方案。它按原样编译和运行。
  • @SLaks:我收到一个错误,'Any' is not a member of EnumerableRowCollection(Of DataRow). 我想我可能导入了错误的库(DataSetExtensions)?不,System.Data.DataTableExtensions 有同样的错误。
  • 你导入了System.Linq 吗?

标签: c# vb.net linq asenumerable


【解决方案1】:

下面是DataTable 的工作示例,如下所示

C#

        DataTable dt = new DataTable();
        dt.Columns.Add("emails");
        dt.Rows.Add("jane@doe.com");
        dt.Rows.Add("mike@foo.com");
        dt.Rows.Add("donald@duck.com");

        var authorized = dt.AsEnumerable().Any(s => s[0].Equals("mike@foo.com")); //returns True
        var notAuthorized = dt.AsEnumerable().Any(s => s[0].Equals("harry@houdini.com"));  //returns False

VB(在线转换)

        Dim dt As DataTable = New DataTable
        dt.Columns.Add("emails")
        dt.Rows.Add("jane@doe.com")
        dt.Rows.Add("mike@foo.com")
        dt.Rows.Add("donald@duck.com")
        Dim authorized As var = dt.AsEnumerable.Any(() => {  }, 
           s(0).Equals("mike@foo.com"))
        Dim notAuthorized As var = dt.AsEnumerable.Any(() => {  }, 
           s(0).Equals("harry@houdini.com"))

【讨论】:

  • 我正在尝试将其翻译成 VB:Dim authorized as Boolean = dt.AsEnumerable().Any(Function(s) s(0).Equals("mike@foo.com"))。我收到此错误:“'Any' 不是 'EnumerableRowCollection(Of DataRow) 的成员”。
  • Imports System.Linq了吗?
  • 啊哈,我认为 DataTableExtensions 拥有所需的一切。导入 Linq。错误消失了。转换 s(0).ToString.ToUpper 后,Any 比较返回 true。谢谢。
  • 谢谢,但这是在线转换的,只是为了给OP提供想法。
【解决方案2】:

Any 在这里可能更干净:

bool exists = dataTable.AsEnumerable()
                       .Any(r => "harry@houdini.com".Equals(r[0]));

可以将该列投影到字符串集合并使用Contains,但在这里似乎有点过头了。

或者定义一个主键,在DataRowCollection上使用原生的Contains方法:

dataTable.PrimaryKey = dataTable.Columns[0];
bool exists = dataTable.Rows.Contains("harry@houdini.com");

【讨论】:

  • 当你想知道一个项目是否包含在一个序列中时,为什么你认为“任何项目都等于这个项目”比使用Contains 更清楚?无需使用集合即可使用Contains
  • 源“集合”是DataTable,因此如果没有DataRow 的主键或自定义相等比较器,Contains 将无法工作。
猜你喜欢
  • 1970-01-01
  • 2012-03-02
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多