我正在構建一個監視用戶計算機上的目錄的WPF應用程序。該應用程序從受監控的目錄中上傳文件,然後將一些信息保存到SQLite數據庫中。部分業務處理是不重新處理已上傳的文件,並重新上傳自上次上傳以來已上傳但已更改的文件。如何讓LINQ全外連接正常工作?
我有兩個幫助器方法,構建並返回一個List<FileMetaData>
,我用LINQ - Full Outer Join加入。我的問題是,當我使用我的FileMetaData
對象時,代碼似乎不起作用。似乎所有的東西都應該可以工作,但是我爲什麼不起作用而不知所措。我通常會嘗試作爲對其他主題的評論發佈,但我目前沒有「Rep」在這裏執行此操作。
下面是我構建的一個示例,顯示我的問題,如果您在LINQpad中運行它。確保在單擊運行按鈕之前將語言設置爲「C#程序」。我應該怎樣做才能使樣本與物體一起工作?萬分感謝!
void Main()
{
var dbItems = new List<FileMetaData>() {
new FileMetaData {FilePath = "C:\\Foo.txt", DbTimestamp = "1" },
new FileMetaData {FilePath = "C:\\FooBar.txt", DbTimestamp = "3" },
};
var fsItems = new List<FileMetaData>() {
new FileMetaData {FilePath = "C:\\Bar.txt", FsTimestamp = "2" },
new FileMetaData {FilePath = "C:\\FooBar.txt", FsTimestamp = "3" },
};
var leftOuter = from d in dbItems
join f in fsItems on d.FilePath equals f.FilePath
into temp
from o in temp.DefaultIfEmpty(new FileMetaData(){})
select new FileMetaData {
FilePath = d.FilePath,
DbTimestamp = d.DbTimestamp,
FsTimestamp = o.FsTimestamp,
};
var rightOuter = from f in fsItems
join d in dbItems on f.FilePath equals d.FilePath
into temp
from o in temp.DefaultIfEmpty(new FileMetaData(){})
select new FileMetaData {
FilePath = f.FilePath,
DbTimestamp = o.DbTimestamp,
FsTimestamp = f.FsTimestamp,
};
var full = leftOuter.AsEnumerable().Union(rightOuter.AsEnumerable());
leftOuter.Dump("Left Results");
rightOuter.Dump("Right Results");
full.Dump("Full Results");
}
// Define other methods and classes here
public class FileMetaData
{
public string FilePath;
public string DbTimestamp;
public string FsTimestamp;
}
編輯:
下面的答案正是我一直在尋找用的。我實現瞭如下定義和改變了我的呼籲var full = leftOuter.Union(rightOuter, new FileMetaDataCompare())
的IEqualityComparer
...
public class FileMetaDataCompare : IEqualityComparer<FileMetaData>
{
public bool Equals(FileMetaData x, FileMetaData y)
{
var areEqual = x.FilePath == y.FilePath;
areEqual = areEqual && x.DbTimestamp == y.DbTimestamp;
areEqual = areEqual && x.FsTimestamp == y.FsTimestamp;
return areEqual;
}
public int GetHashCode(FileMetaData obj)
{
var hCode = string.Concat(obj.FilePath, obj.DbTimestamp, obj.FsTimestamp);
return hCode.GetHashCode();
}
}
非常感謝你的回答。我在IEqualityComparer上完全消隱了。 – Frito 2012-07-24 18:38:08