[英]Is there an easy way to INNER join , OUTER join , LEFT OUTER join, RIGHT OUTER join, or UNION two (or more) DataTables in C#?
I am writing ac# application that connects separate database systems. 我正在编写连接单独的数据库系统的ac#应用程序。 These systems could be flat-file db's, Oracle, Sql, Excel Files, ext. 这些系统可以是平面文件数据库,Oracle,Sql,Excel文件等。 The job of the C# application is to provide an outlet for making all of these sources available in one spot. C#应用程序的工作是提供一个出口,使所有这些资源都可以在一个地方使用。 So basically, the application accepts a list of queries and connection settings for the respective database systems and collects a bunch of results. 因此,基本上,该应用程序接受相应数据库系统的查询和连接设置的列表,并收集大量结果。
The goal is to output a singe DataTable with the result of all these queries all joined/unioned together(depending on settings). 目标是输出一个单数据表,其中所有这些查询的结果全部联接/联合在一起(取决于设置)。 Does C# provide an easy way to perform any join/union operations on a list of DataTables? C#是否提供一种简便的方法来对DataTables列表执行任何联接/联合操作?
For example: 例如:
Table1:
__________________________________________________________
|tb1_pk_id| tb1_name | tb1_data1 | tb1_data2 |
|---------|---------------|---------------|---------------|
| 1 | tb1name_blah1 | tb1dat1_blah1 | tb1dat2blah1 |
| 2 | tb1name_blah2 | tb1dat1_blah2 | tb1dat2blah2 |
| 3 | tb1name_blah3 | tb1dat1_blah3 | tb1dat2blah3 |
-----------------------------------------------------------
Table2:
__________________________________________________________
|tb2_pk_id| tb2_name | tb2_data1 | tb2_data2 |
|---------|---------------|---------------|---------------|
| 1 | tb2name_blah1 | tb2dat1_blah1 | tb2dat2blah1 |
| 2 | tb2name_blah2 | tb2dat1_blah2 | tb2dat2blah2 |
| 3 | tb2name_blah3 | tb2dat1_blah3 | tb2dat2blah3 |
-----------------------------------------------------------
Join Results:
__________________________________________________________ _______________________________________________
|tb1_pk_id| tb1_name | tb1_data1 | tb1_data2 | tb2_name | tb2_data1 | tb2_data2 |
|---------|---------------|---------------|---------------|---------------|---------------|---------------|
| 1 | tb1name_blah1 | tb1dat1_blah1 | tb1dat2blah1 | tb2name_blah1 | tb2dat1_blah1 | tb2dat2blah1 |
| 2 | tb1name_blah2 | tb1dat1_blah2 | tb1dat2blah2 | tb2name_blah2 | tb2dat1_blah2 | tb2dat2blah2 |
| 3 | tb1name_blah3 | tb1dat1_blah3 | tb1dat2blah3 | tb2name_blah3 | tb2dat1_blah3 | tb2dat2blah3 |
-----------------------------------------------------------------------------------------------------------
So far I have found the following code online ( here ) to do a merge on all the data: 到目前为止,我已经在线找到了以下代码( 此处 )以对所有数据进行合并:
private DataTable MergeAll(IList<DataTable> tables, String primaryKeyColumn)
{
if (!tables.Any())
throw new ArgumentException("Tables must not be empty", "tables");
if (primaryKeyColumn != null)
foreach (DataTable t in tables)
if (!t.Columns.Contains(primaryKeyColumn))
throw new ArgumentException("All tables must have the specified primarykey column " + primaryKeyColumn, "primaryKeyColumn");
if (tables.Count == 1)
return tables[0];
DataTable table = new DataTable("TblUnion");
table.BeginLoadData(); // Turns off notifications, index maintenance, and constraints while loading data
foreach (DataTable t in tables)
{
table.Merge(t); // same as table.Merge(t, false, MissingSchemaAction.Add);
}
table.EndLoadData();
if (primaryKeyColumn != null)
{
// since we might have no real primary keys defined, the rows now might have repeating fields
// so now we're going to "join" these rows ...
var pkGroups = table.AsEnumerable()
.GroupBy(r => r[primaryKeyColumn]);
var dupGroups = pkGroups.Where(g => g.Count() > 1);
foreach (var grpDup in dupGroups)
{
// use first row and modify it
DataRow firstRow = grpDup.First();
foreach (DataColumn c in table.Columns)
{
if (firstRow.IsNull(c))
{
DataRow firstNotNullRow = grpDup.Skip(1).FirstOrDefault(r => !r.IsNull(c));
if (firstNotNullRow != null)
firstRow[c] = firstNotNullRow[c];
}
}
// remove all but first row
var rowsToRemove = grpDup.Skip(1);
foreach (DataRow rowToRemove in rowsToRemove)
table.Rows.Remove(rowToRemove);
}
}
return table;
}
This works fine for doing a union, but I don't know if an easier way to do that already exists in .NET that will let me do ANY kind of join or union on a group of seprate DataTables (not just the union as in the code above) or do I have to custom code each type of join/union? 这对于进行合并非常有效,但是我不知道.NET中是否已经存在一种更简单的方法,该方法可以让我对一组单独的DataTables进行任何类型的联接或联合(而不仅仅是像这样的联合)上面的代码)还是我必须自定义每种联接/联合类型的代码?
No, there is not a simple .Net way of doing this.... 不,没有简单的.Net方法可以执行此操作。
LINQ can come close... you can create table joins in LINQ, but they are typically "inner joins". LINQ可以接近...您可以在LINQ中创建表联接,但是它们通常是“内部联接”。 Doing a "left join" is a bit more complicated and requires the GroupJoin
keyword. 进行“左连接”要复杂一些,并且需要使用GroupJoin
关键字。 https://msdn.microsoft.com/en-us/library/bb386969(v=vs.110).aspx https://msdn.microsoft.com/en-us/library/bb386969(v=vs.110).aspx
If you'd like "do it yourself" with ADO.Net DataRelations, you might take a look at this old VB.Net article: 如果您想使用ADO.Net DataRelations“自己动手”,则可以看一下这篇旧的VB.Net文章:
http://www.emmet-gray.com/Articles/DataRelations.html http://www.emmet-gray.com/Articles/DataRelations.html
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.