使用 C# 的比较和同步工具






2.92/5 (5投票s)
2005 年 11 月 10 日
2分钟阅读

29496

627
本文介绍了一个使用 C# 编写的比较/同步工具。
引言
本文介绍了一个使用 C# 编写的比较/同步工具。该控件最初是为不同数据库(生产数据库和测试数据库)中两个表的同步而创建的。然而,我注意到它可以扩展为比较和同步任何类型的对象。文章中提供的演示用于比较和同步基于字符串的键值对。
设计
控件的结构如图所示
控件接收两种类型的集合作为输入,类型为 CompareCollection
public void DisplayCollections ( CompareCollection A,
CompareCollection B )
CompareCollection
实现 ICollection
接口,并包含类型为 CompareItem
的对象。CompareItem
类包含以下成员
private object m_sKey;
private object m_sValue;
private object m_sNewKey;
private object m_sNewValue;
private bool m_bWasAdded = false;
private bool m_bWasModified = false;
private bool m_bWasDeleted = false;
private bool m_bIsDifferentKey = false;
private bool m_bIsDifferentValue = false;
private bool m_bIsDummy = false;
private bool m_bIsReadOnly = false;
Key
是类的一个重要成员。Key
用于在 ListBox
中放置对象。例如:只有当两个 string
对象具有相同的键时,它们才会在两个 ListBox
的同一行中显示。(如果项目的数值不同,则包含这些项目的行将被突出显示。)
大多数标志都易于理解,除了 IsDifferentKey
和 IsDifferentValue
。请注意,iCompareKey
和 iCompareValue
是 CompareItem
的 virtual
函数,应该为适当的对象进行重写。在本例中,键和值都转换为 string
类型进行比较。
类的另一个 virtual
参数是 sDisplayString
,它用于在 ListBox
中显示一个 string
。大部分逻辑都集中在 LineComparatorControl
类中。主要函数是
DoDisplayCollections
:该函数将项目放置在ListBox
中private void DoDisplayCollections ( CompareCollection oLeft, CompareCollection oRight ) { int iLeftIndex = 0; int iRightIndex = 0; int iSyncIndex = 0; while ( iLeftIndex < oLeft.Count || iRightIndex < oRight.Count ){ // Compare int iCompResult = 0; if ( iLeftIndex == oLeft.Count ) { iCompResult = 1; }else if ( iRightIndex == oRight.Count ){ iCompResult = -1; }else{ iCompResult = oLeft[iLeftIndex].iCompareKey( oRight[iRightIndex] ); } // Print List Box if ( iCompResult < 0 ){ // Print Left Side Only oLeft[iLeftIndex].bDifferentKey = true; LeftListBox.Items.Insert (iSyncIndex, oLeft[iLeftIndex]); RightListBox.Items.Insert (iSyncIndex, new CompareItem( true, true, true ) ); iLeftIndex++; }else if ( iCompResult > 0 ){ // Print Right Side Only oRight[iRightIndex].bDifferentKey = true; RightListBox.Items.Insert (iSyncIndex, oRight[iRightIndex] ); LeftListBox.Items.Insert (iSyncIndex, new CompareItem( true, true, true ) ); iRightIndex++; }else{ if (oLeft[iLeftIndex].iCompareValue(oRight[iRightIndex]) != 0 ){ oRight[iRightIndex].bDifferentValue = true; oLeft[iLeftIndex].bDifferentValue = true; } RightListBox.Items.Insert ( iSyncIndex, oRight[iRightIndex] ); LeftListBox.Items.Insert ( iSyncIndex, oLeft[iLeftIndex] ); iLeftIndex++; iRightIndex++; } iSyncIndex++; } }
bExecuteSync
:此函数用于同步项目。如果同步失败,该函数会弹出一个包含错误消息的消息框。为了检查是否可以进行同步,使用了一个
virtual
函数bIsSynchronizationOk
。private bool bExecuteSync ( CompareItem oFromItem, CompareItem oToItem, ref string sErrorMsg ){ if ( oFromItem.bDummy ){ oToItem.bDeleted = true; }else if ( oToItem.bDummy ){ oToItem.bAdded = true; oToItem.sNewKey = oFromItem.sKey; oToItem.sNewValue = oFromItem.sValue; }else { oToItem.bModified = true; oToItem.sNewKey = oFromItem.sKey; oToItem.sNewValue = oFromItem.sValue; } if ( bIsSynchronizationOk ( oToItem, ref sErrorMsg ) ){ if ( !oToItem.bDeleted ){ oToItem.sKey = oToItem.sNewKey; oToItem.sValue = oToItem.sNewValue; } if ( oToItem.bDeleted || oToItem.bAdded ){ oToItem.bDummy = false; oFromItem.bDummy = false; } oToItem.bDifferentKey = false; oToItem.bDifferentValue = false; oFromItem.bDifferentKey = false; oFromItem.bDifferentValue = false; return true; }else{ return false; } }
为了实现您自己更改项目的存储逻辑,您需要重写函数 LeftStoreButton_Click
和 RightStoreButton_Click
。
希望本文对您有所帮助。
参考文献
为了突出显示 ListBox
中的行,我使用了文章:A C# ColorListBox。