以编程方式比较word文档

我需要比较两个办公文档,在这种情况下是两个word文档并提供差异,这有点类似于SVN中显示的内容。 不是那么大,但至少能够突出差异。

我尝试使用办公室COM DLL,并得到了这个…

object fileToOpen = (object)@"D:\doc1.docx"; string fileToCompare = @"D:\doc2.docx"; WRD.Application WA = new WRD.Application(); Document wordDoc = null; wordDoc = WA.Documents.Open(ref fileToOpen, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing); wordDoc.Compare(fileToCompare, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing); 

有关如何进一步处理的任何提示? 这将是一个具有大量点击的Web应用程序。 使用office com对象是正确的方法,还是有其他我可以看的东西?

我同意约瑟夫关于区分弦乐的事。 我还推荐一个专用的diffing引擎(这里有几个: .NET的任何体面的文本差异/合并引擎? ),它可以帮助你避免一些正常的差异陷阱。

您应该使用Document类来比较文件,并在Word文档中打开结果。

 using OfficeWord = Microsoft.Office.Interop.Word; object fileToOpen = (object)@"D:\doc1.docx"; string fileToCompare = @"D:\doc2.docx"; var app = Global.OfficeFile.WordApp; object readOnly = false; object AddToRecent = false; object Visible = false; OfficeWord.Document docZero = app.Documents.Open(fileToOpen, ref missing, ref readOnly, ref AddToRecent, Visible: ref Visible); docZero.Final = false; docZero.TrackRevisions = true; docZero.ShowRevisions = true; docZero.PrintRevisions = true; //the OfficeWord.WdCompareTargetNew defines a new file, you can change this valid value to change how word will open the document docZero.Compare(fileToCompare, missing, OfficeWord.WdCompareTarget.wdCompareTargetNew, true, false, false, false, false); 

所以我的要求是我必须使用.Net lib,我想避免处理实际文件但是使用流。

ZipArchive在System.IO.Compressed中

我做的很好,并且很好地使用了来自.Net的ZipArchive并在跳过.rels文件时比较内容,因为它似乎是在每个文件创建时随机生成的。 这是我的片段:

  private static bool AreWordFilesSame(byte[] wordA, byte[] wordB) { using (var streamA = new MemoryStream(wordA)) using (var streamB = new MemoryStream(wordB)) using (var zipA = new ZipArchive(streamA)) using (var zipB = new ZipArchive(streamB)) { streamA.Seek(0, SeekOrigin.Begin); streamB.Seek(0, SeekOrigin.Begin); for(int i = 0; i < zipA.Entries.Count; ++i) { Assert.AreEqual(zipA.Entries[i].Name, zipB.Entries[i].Name); if (zipA.Entries[i].Name.EndsWith(".rels")) //These are some weird word files with autogenerated hashes { continue; } var streamFromA = zipA.Entries[i].Open(); var streamFromB = zipB.Entries[i].Open(); using (var readerA = new StreamReader(streamFromA)) using (var readerB = new StreamReader(streamFromB)) { var bytesA = readerA.ReadToEnd(); var bytesB = readerB.ReadToEnd(); if (bytesA != bytesB || bytesA.Length == 0) { return false; } } } return true; } } 

你应该把文档解压缩成一个字符串并将其区分开来。

你只关心文本的变化而不是格式化吗?

要进行Word文档之间的比较,您需要

  1. 用于操作Word文档的库,例如从Word文件中读取段落,文本,表格等。 您可以尝试使用Office Interop,OpenXML或Aspose.Words for .NET 。
  2. 对从两个Word文档检索的文本进行实际比较的算法/库。 您可以自己编写或使用像DiffMatchPatch或类似的库。

这个问题很老,现在有更多的解决方案,如GroupDocs Compare可用。

Aspose.Words for .NET的文档比较是一个开源展示项目,它使用Aspose.Words和DiffMatchPatch进行比较。

我在Aspose担任开发人员传播者。

对于服务器上的解决方案,或者在没有安装Word和使用COM工具的情况下运行,您可以使用XmlPowerTools的WmlComparer组件。

文档有点受限,但这是一个示例用法:

 var expected = File.ReadAllBytes(@"c:\expected.docx"); var actual = File.ReadAllBytes(@"c:\result.docx"); var expectedresult = new WmlDocument("expected.docx", expected); var actualDocument = new WmlDocument("result.docx", actual); var comparisonSettings = new WmlComparerSettings(); var comparisonResults = WmlComparer.Compare(expectedresult, actualDocument, comparisonSettings); var revisions = WmlComparer.GetRevisions(comparisonResults, comparisonSettings); 

这将显示两个文件之间的差异。