Tôi có danh sách kiểm tra đầy đủ các đối tượng được tuần tự hóa và tôi muốn so sánh chúng và trả về danh sách các khác biệt. Bằng cách 'so sánh', tôi muốn quay lại vị trí văn bản cho phần tử đã thay đổi hoặc vị trí nút đã được thêm vào (vì vậy nó không có trong Xml1, nhưng nó nằm trong Xml2- nó sẽ không xảy ra theo cách khác)So sánh các phân đoạn XML và các khác biệt trả về
mẫu xml:
<HotelBookingView xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<Id>119</Id>
<RoomId>1</RoomId>
<ChangeRequested>false</ChangeRequested>
<CourseBookings>
<CourseHotelLink>
<Id>0</Id>
</CourseHotelLink>
</CourseBookings>
</HotelBookingView>
các không gian tên và tên/trường hợp các thẻ sẽ không thay đổi. Tất cả những gì có thể thay đổi trong mẫu này là các giá trị giữa các thẻ và số 'CourseHotelLink's (một danh sách được sắp xếp theo thứ tự).
Kết quả cuối cùng tôi muốn là danh sách nút đã thay đổi - giá trị cũ và giá trị mới.
Tùy chọn nào tốt nhất để so sánh chúng? Tôi đang sử dụng. Net 4.0 để linq là một lựa chọn. Tôi cần để có thể làm so sánh mà không nhất thiết phải biết tên của tất cả các nút- mặc dù tôi sẽ chỉ bao giờ so sánh hai đối tượng cùng loại. Tôi đã cố gắng sử dụng mã sau đây, nhưng tôi không thể quản lý để thích ứng với nó để chọn ra các thay đổi trong văn bản cũng như các nút bổ sung.
XmlDocument Xml1 = new XmlDocument();
XmlDocument Xml2 = new XmlDocument();
Xml1.LoadXml(list[1].Changes);
Xml2.LoadXml(list[2].Changes);
foreach (XmlNode chNode in Xml2.ChildNodes)
{
CompareLower(chNode);
}
protected void CompareLower(XmlNode aNode)
{
foreach (XmlNode chlNode in aNode.ChildNodes)
{
string Path = CreatePath(chlNode);
if (chlNode.Name == "#text")
{
//all my efforts at comparing text have failed
continue;
}
if (Xml1.SelectNodes(Path).Count == 0)
{
XmlNode TempNode = Xml1.ImportNode(chlNode, true);
//node didn't used to exist, this works- though doesn't return values
str = str + "New Node: " + TempNode.Name + ": " + TempNode.Value;
}
else
{
CompareLower(chlNode);
}
}
}
của nó có khả năng nỗ lực mã của tôi là dặm ngoài khơi và có một cách tốt hơn nhiều việc phải làm, bất cứ đề nghị chào đón!
EDITTED để thêm: Tôi đã kết thúc bằng công cụ MS Xml Diff, đoạn mã sau tạo danh sách bảng html lớn của hai nút xml, với sự khác biệt được đánh dấu bằng màu xanh lục. Vì vậy, nó có thể (mặc dù điên) để sản xuất html, sau đó sắp xếp thông qua nó để tìm văn bản 'lightgreen' (giá trị được đánh dấu), sau đó thực hiện một số hình dạng chuỗi để chỉ hiển thị nút con đã thay đổi.
var node1 = XElement.Parse("Xml string 1 here").CreateReader();
var node2 = XElement.Parse("Xml string 2 here").CreateReader();
MemoryStream diffgram = new MemoryStream();
XmlTextWriter diffgramWriter = new XmlTextWriter(new StreamWriter(diffgram));
XmlDiff xmlDiff = new XmlDiff(XmlDiffOptions.IgnoreChildOrder);
xmlDiff.Algorithm = XmlDiffAlgorithm.Fast;
xmlDiff.Compare(node1, node2,diffgramWriter);
diffgram.Seek(0, SeekOrigin.Begin);
XmlDiffView xmlDiffView = new Microsoft.XmlDiffPatch.XmlDiffView();
StringBuilder sb = new StringBuilder();
TextWriter resultHtml = new StringWriter(sb);
xmlDiffView.Load("Xml string 1", new XmlTextReader(diffgram));
xmlDiffView.GetHtml(resultHtml);
resultHtml.Close();
Hãy xem bài này: http://stackoverflow.com/question/167946/how-would-bạn-so sánh-hai-xml-documents –
Tôi chưa biết làm thế nào để có được MS Diff và Patch để lấy các chuỗi XML - XML của tôi xuất phát từ một cơ sở dữ liệu và tôi không muốn phải tạo tệp mỗi lần tôi muốn t o sử dụng nó ... Chỉ có thể là tôi dày đặc. – UglyTeapot
Bạn không cần phải tạo tệp, nó đi kèm với nhiều quá tải để so sánh tệp, XmlTextReader hoặc XmlNode –