1102

DataTable オブジェクトで LINQ クエリを実行しようとしていますが、奇妙なことに、DataTables でそのようなクエリを実行するのは簡単ではありません。例えば:

var results = from myRow in myDataTable
where results.Field("RowNo") == 1
select results;

これは許可されていません。このようなものを機能させるにはどうすればよいですか?

DataTable で LINQ クエリが許可されていないことに驚きました。

4

22 に答える 22

1353

は を実装していないため、DataTableRowsコレクションに対してクエリを実行することはできません。の拡張子を使用する必要があります。そのようです:DataRowCollectionIEnumerable<T>AsEnumerable()DataTable

var results = from myRow in myDataTable.AsEnumerable()
where myRow.Field<int>("RowNo") == 1
select myRow;

@Keithが言うように、 System.Data.DataSetExtensionsへの参照を追加する必要があります。

AsEnumerable()戻りますIEnumerable<DataRow>IEnumerable<DataRow>に変換する必要がある場合は、拡張子DataTableを使用してください。CopyToDataTable()

以下は、ラムダ式を使用したクエリです。

var result = myDataTable
    .AsEnumerable()
    .Where(myRow => myRow.Field<int>("RowNo") == 1);
于 2008-08-14T19:45:01.383 に答える
139
var results = from DataRow myRow in myDataTable.Rows
    where (int)myRow["RowNo"] == 1
    select myRow
于 2009-03-05T02:53:10.860 に答える
74

これらが意図的に DataTable で許可されなかったわけではありません。単に DataTable が、Linq クエリを実行できる IQueryable およびジェネリック IEnumerable 構造よりも古いというだけです。

両方のインターフェイスには、ある種のタイプ セーフ検証が必要です。DataTables は厳密に型指定されていません。これは、たとえば、人々が ArrayList に対してクエリを実行できないのと同じ理由です。

Linq が機能するには、結果を型保証オブジェクトにマップし、代わりにそれに対してクエリを実行する必要があります。

于 2008-08-14T10:10:55.917 に答える
53

@ch00kが言ったように:

using System.Data; //needed for the extension methods to work

...

var results = 
    from myRow in myDataTable.Rows 
    where myRow.Field<int>("RowNo") == 1 
    select myRow; //select the thing you want, not the collection

また、プロジェクト参照を追加する必要がありますSystem.Data.DataSetExtensions

于 2008-08-14T11:07:52.613 に答える
43

これは何度か回答されていることを認識していますが、別のアプローチを提供するためだけに:

私はメソッドを使用するのが好き.Cast<T>()です.明示的な型が定義されていることを確認する際に正気を維持するのに役立ちます..AsEnumerable()とにかくそれを呼び出すと思います:

var results = from myRow in myDataTable.Rows.Cast<DataRow>() 
                  where myRow.Field<int>("RowNo") == 1 select myRow;

また

var results = myDataTable.Rows.Cast<DataRow>()
                  .FirstOrDefault(x => x.Field<int>("RowNo") == 1);

コメントに記載されているように、System.Data.DataSetExtensionsその他のアセンブリは必要ありません (参照)

于 2016-02-02T21:22:20.983 に答える
40
var query = from p in dt.AsEnumerable()
                    where p.Field<string>("code") == this.txtCat.Text
                    select new
                    {
                        name = p.Field<string>("name"),
                        age= p.Field<int>("age")                         
                    };

name フィールドと age フィールドはクエリ オブジェクトの一部になり、次のようにアクセスできます

于 2010-05-23T04:03:29.717 に答える
31

LINQ を使用して DataSet/DataTable のデータを操作する

var results = from myRow in tblCurrentStock.AsEnumerable()
              where myRow.Field<string>("item_name").ToUpper().StartsWith(tbSearchItem.Text.ToUpper())
              select myRow;
DataView view = results.AsDataView();
于 2011-07-13T11:21:07.110 に答える
30
//Create DataTable 
DataTable dt= new DataTable();
dt.Columns.AddRange(new DataColumn[]
{
   new DataColumn("ID",typeof(System.Int32)),
   new DataColumn("Name",typeof(System.String))

});

//Fill with data

dt.Rows.Add(new Object[]{1,"Test1"});
dt.Rows.Add(new Object[]{2,"Test2"});

//Now  Query DataTable with linq
//To work with linq it should required our source implement IEnumerable interface.
//But DataTable not Implement IEnumerable interface
//So we call DataTable Extension method  i.e AsEnumerable() this will return EnumerableRowCollection<DataRow>


// Now Query DataTable to find Row whoes ID=1

DataRow drow = dt.AsEnumerable().Where(p=>p.Field<Int32>(0)==1).FirstOrDefault();
 // 
于 2012-01-05T08:43:15.667 に答える
24

次の簡単なクエリ行を試してください。

var result=myDataTable.AsEnumerable().Where(myRow => myRow.Field<int>("RowNo") == 1);
于 2016-04-05T09:38:59.350 に答える
17

次のように、Rows コレクションのオブジェクトに対して LINQ を使用できます。

var results = from myRow in myDataTable.Rows where myRow.Field("RowNo") == 1 select myRow;
于 2008-08-14T10:11:08.787 に答える
11

これを試して

var row = (from result in dt.AsEnumerable().OrderBy( result => Guid.NewGuid()) select result).Take(3) ; 
于 2012-05-18T07:15:08.957 に答える
11

ほとんどの場合、DataSet、DataTable、および DataRow のクラスはソリューションで既に定義されています。その場合、DataSetExtensions 参照は必要ありません。

元。DataSet クラス名 -> CustomSet、DataRow クラス名 -> CustomTableRow (定義された列: RowNo、...)

var result = from myRow in myDataTable.Rows.OfType<CustomSet.CustomTableRow>()
             where myRow.RowNo == 1
             select myRow;

または(私が好むように)

var result = myDataTable.Rows.OfType<CustomSet.CustomTableRow>().Where(myRow => myRow.RowNo);
于 2013-04-24T17:17:47.570 に答える
9
var results = from myRow in myDataTable
where results.Field<Int32>("RowNo") == 1
select results;
于 2014-02-01T11:51:43.540 に答える
8

私のアプリケーションでは、回答で提案されているように、DataTable の AsEnumerable() 拡張機能を使用して LINQ to Datasets を使用すると、非常に遅いことがわかりました。速度の最適化に関心がある場合は、James Newtonking の Json.Net ライブラリ ( http://james.newtonking.com/json/help/index.html )を使用してください。

// Serialize the DataTable to a json string
string serializedTable = JsonConvert.SerializeObject(myDataTable);    
Jarray dataRows = Jarray.Parse(serializedTable);

// Run the LINQ query
List<JToken> results = (from row in dataRows
                    where (int) row["ans_key"] == 42
                    select row).ToList();

// If you need the results to be in a DataTable
string jsonResults = JsonConvert.SerializeObject(results);
DataTable resultsTable = JsonConvert.DeserializeObject<DataTable>(jsonResults);
于 2014-10-14T17:51:10.997 に答える
7
IEnumerable<string> result = from myRow in dataTableResult.AsEnumerable()
                             select myRow["server"].ToString() ;
于 2015-08-04T07:32:55.757 に答える
7

VB.NET の場合、コードは次のようになります。

Dim results = From myRow In myDataTable  
Where myRow.Field(Of Int32)("RowNo") = 1 Select myRow
于 2012-10-17T16:04:52.607 に答える
5

次のようにlinqを介してエレガントに動作させることができます:

from prod in TenMostExpensiveProducts().Tables[0].AsEnumerable()
where prod.Field<decimal>("UnitPrice") > 62.500M
select prod

または、動的 linq のように (AsDynamic は DataSet で直接呼び出されます):

TenMostExpensiveProducts().AsDynamic().Where (x => x.UnitPrice > 62.500M)

私は最後のアプローチを好みますが、これが最も柔軟です。System.Data.DataSetExtensions.dllPS:参照を接続することを忘れないでください

于 2013-11-03T17:54:15.080 に答える