datatable 求交集

billow007 2009-05-27 05:03:38
两个同样结构的表,其中部分数据行相同,如何求交集呢?
只能一条一条取出来比对么?比如用select 其中的一行的某个字段值等于另一个表的某行的同字段值的话,
把这一行选出来。
...全文
404 23 打赏 收藏 转发到动态 举报
写回复
用AI写文章
23 条回复
切换为时间正序
请发表友善的回复…
发表回复
hugofgh 2012-02-27
  • 打赏
  • 举报
回复
good
心向明月 2011-10-12
  • 打赏
  • 举报
回复
//首先要添加System.Data.DataSetExtensions;
DataSet ds = new DataSet();
ds.Locale = CultureInfo.InvariantCulture;
FillDataSet(ds);

DataTable contactTable = ds.Tables["Contact"];

// Create two tables.
IEnumerable<DataRow> query1 = from contact in contactTable.AsEnumerable()
where contact.Field<string>("Title") == "Ms."
select contact;

IEnumerable<DataRow> query2 = from contact in contactTable.AsEnumerable()
where contact.Field<string>("FirstName") == "Sandra"
select contact;


DataTable contacts1 = query1.CopyToDataTable();
DataTable contacts2 = query2.CopyToDataTable();

// Find the intersection of the two tables. 求交集用 Intersect/Union(并集)/Except(差集)
var contacts = contacts1.AsEnumerable().Intersect(contacts2.AsEnumerable(),
DataRowComparer.Default);

Console.WriteLine("Intersection of contacts tables");
foreach (DataRow row in contacts)
{
Console.WriteLine("Id: {0} {1} {2} {3}",
row["ContactID"], row["Title"], row["FirstName"], row["LastName"]);
}


DbHelperSQL.connectionString = strSiteConnection;
DataTable dtblSiteTable = DbHelperSQL.TQuery("Select * From " + strTableName);
IEnumerable<DataRow> querySite = from contact in dtblSiteTable.AsEnumerable() select contact;

DbHelperSQL.connectionString = strMainConnection;
DataTable dtblMainTable = DbHelperSQL.TQuery("Select * From " + strTableName);
IEnumerable<DataRow> queryMain = from contact in dtblMainTable.AsEnumerable() select contact;

var EnumerableExcept = querySite.CopyToDataTable().AsEnumerable().Except(queryMain.CopyToDataTable().AsEnumerable(), DataRowComparer.Default);

DataTable dtblExcept = EnumerableExcept.CopyToDataTable(); //dtblExcept 即为差异的数据表

摘抄自:http://www.cnblogs.com/zhangpengshou/archive/2010/06/30/1768384.html
getcodein 2010-12-18
  • 打赏
  • 举报
回复
asdfsdgfdgsdg
zhang_zdx 2009-07-14
  • 打赏
  • 举报
回复
学习了 受教 谢谢
kldx5092 2009-05-27
  • 打赏
  • 举报
回复
DataRelation
cppfaq 2009-05-27
  • 打赏
  • 举报
回复
用LINQ搞定
dataTable.AsEnumerable().Intersect(dataTable2.AsEnumerable(), DataRowComparer.Default)
using System;
using System.Data;
using System.Linq;

namespace ConsoleApplication1
{
internal class Program
{
private static void Main()
{
var dataTable = new DataTable();
dataTable.Columns.Add("A");
dataTable.Columns.Add("B");
dataTable.Columns.Add("C");
dataTable.Rows.Add("1", "2", "3");
dataTable.Rows.Add("1", "2", "4");
dataTable.Rows.Add("2", "2", "3");
dataTable.Rows.Add("5", "2", "1");
dataTable.AcceptChanges();

var dataTable2 = new DataTable();
dataTable2.Columns.Add("A");
dataTable2.Columns.Add("B");
dataTable2.Columns.Add("C");
dataTable2.Rows.Add("1", "2", "3");
dataTable2.Rows.Add("1", "2", "4");
dataTable2.Rows.Add("2", "2", "3");
dataTable2.Rows.Add("5", "2", "1");
dataTable2.AcceptChanges();

Console.WriteLine("A\tB\tC");
foreach (
DataRow dataRow in
dataTable.AsEnumerable().Intersect(dataTable2.AsEnumerable(), DataRowComparer.Default))
{
Console.WriteLine(dataRow[0] + "\t" + dataRow[1] + "\t" + dataRow[2]);
}

Console.ReadLine();
}
}
}
缥缈大木头 2009-05-27
  • 打赏
  • 举报
回复
说实话,不管你在两次循环里面作什么,都效率不高。
楼主想要的就是一个时间复杂度更低的方法吧。

[Quote=引用 3 楼 wood001 的回复:]
嘿嘿,想到一个邪恶的方法,利用
try{}catch{}

把一个表里的行向另一个表里插,插不进的就是交集数据,
在catch里面写到交集表里面。
[/Quote]

如果楼主的DataTable是个有主键的DataTable,可以尝试一下这个。

foreach (DataRow dr in data1.Rows) {
try {
data2.ImportRow(dr);
} catch {
data3.ImportRow(dr);
}
}
frankonlyfine 2009-05-27
  • 打赏
  • 举报
回复
准备要下班了.端午节过会如果你还没搞定到时再来帮你搞..
ch5201314zt 2009-05-27
  • 打赏
  • 举报
回复

写SQL语句啊

select a.*,b.* from TableA left join TableB on a.相同的字段=b.相同的字段

就可以实现你要的效果了,你试试!

参考
frankonlyfine 2009-05-27
  • 打赏
  • 举报
回复
我的思路是先把那张源数据库合到dsTempValue这个表里,然后新建个空表.在源数据库表里做每行每列循环,把每行每列的值合并成一个字符串加到List里,然后在空表里添加行的时候判断list里是否有相同数据,如果有则不添加.这样就不会有重复数据了


DataTable dtTarget = new DataTable();
List<string> lsKeys = new List<string>();
foreach (DataRow row in dsTempValue.Tables[1].Rows)//循环每行
{

drTarget = dtTarget.NewRow();
string key = "";
foreach (DataColumn col in dsTempValue.Tables[1].Columns)//循环每列
{


key += row[col.ColumnName].ToString();
drTarget[col.ColumnName] = row[col.ColumnName];

}
if (!lsKeys.Contains(key))//判断是否已经有相同数据
{
dtTarget.Rows.Add(drTarget);
}
lsKeys.Add(key);
}
closewbq 2009-05-27
  • 打赏
  • 举报
回复
不知道是否可行,你可以将数据库中的每条数据看成一个类对象,将两个表的所有对象都添加到两个LIST中,循环遍历对象,看那些对象相等就取出来。
cppfaq 2009-05-27
  • 打赏
  • 举报
回复
仔细看下面的comments
cppfaq 2009-05-27
  • 打赏
  • 举报
回复
参考这个
http://weblogs.sqlteam.com/davidm/archive/2004/01/21/753.aspx

目前想不到更好的
zhaoweiting0609 2009-05-27
  • 打赏
  • 举报
回复
[Quote=引用 5 楼 zhulong1111 的回复:]
你可以先把一个表的数据全部插入到另个表里面 然后在另一个表根据分组大于1的就是他们两个表的交集了哦
[/Quote]

这个想法也不错,更快
billow007 2009-05-27
  • 打赏
  • 举报
回复
[Quote=引用 7 楼 frankonlyfine 的回复:]
楼主我有办法哈哈,我做过这样的判断.先占个楼.我慢慢写给你.到时分要全部给我哦
[/Quote]
如果您的方法好,我给你加倍,当然其他人我也会给分的
huangheping520hhp 2009-05-27
  • 打赏
  • 举报
回复
关注
frankonlyfine 2009-05-27
  • 打赏
  • 举报
回复
楼主我有办法哈哈,我做过这样的判断.先占个楼.我慢慢写给你.到时分要全部给我哦
zhaoweiting0609 2009-05-27
  • 打赏
  • 举报
回复
[Quote=引用楼主 billow007 的帖子:]
两个同样结构的表,其中部分数据行相同,如何求交集呢?
只能一条一条取出来比对么?比如用select 其中的一行的某个字段值等于另一个表的某行的同字段值的话,
把这一行选出来。
[/Quote]

楼主的思路也不错啊
用一个for循环,循环一个表
如果是sql的话,用if exists判断会快点
如果exists就add
else continue
这个效率上不会太差吧

期待高手给更好的答案
zhulong1111 2009-05-27
  • 打赏
  • 举报
回复
你可以先把一个表的数据全部插入到另个表里面 然后在另一个表根据分组大于1的就是他们两个表的交集了哦
缥缈大木头 2009-05-27
  • 打赏
  • 举报
回复
[Quote=引用 3 楼 wood001 的回复:]
嘿嘿,想到一个邪恶的方法,利用
try{}catch{}

把一个表里的行向另一个表里插,插不进的就是交集数据,
在catch里面写到交集表里面。
[/Quote]
纯属YY,不要尝试
加载更多回复(3)

110,567

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Web++
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

让您成为最强悍的C#开发者

试试用AI创作助手写篇文章吧