我有一个dataTable,我将使用BulkCopy到目标表 . 我正在尝试解决主键违规问题 . 因此,我没有使用临时表,而是与 生产环境 合并,而是尝试从内存中的DataTable中删除冗余行,然后再将其传递给WriteToServer方法 .
在我的代码中,我根据列和字段以与数据库中的表格相同的格式创建了Memory DataTable列 . 所以我没有做任何列映射 . 我的PK记录是具有唯一值约束的GUID,称为PKID . 我从磁盘上的CSV文件填充DataTable然后执行BulkCopy .
我的想法是尝试执行以下逻辑: Delete From MemoryDataTable where PKID is in (SELECT PKID from SQLTable)
这是我的代码:
Try
Using sqlBulk As New SqlBulkCopy(LocalDBConnectionString, SqlBulkCopyOptions.TableLock)
sqlBulk.DestinationTableName = "DataRecords"
sqlBulk.BatchSize = 5000
sqlBulk.WriteToServer(MemoryDataTable)
sqlBulk.Close()
End Using
Catch ex As Exception
EventArgs.ErrorMessage = ex.Message
''''Catch Primary Key Violation Here''''
End Try
2 回答
你不能这样做,因为MemoryDataTable只存在于你的vb.net程序的上下文中,即SQL / Server对此一无所知 .
但是,您可以将内存表加载到服务器上的临时表,然后执行您喜欢的任何SQL操作 . 例如 .
然后将您的SqlBulk加载到#TempDataTable中,并且1)将#TempDataTable合并到SQLTable中或执行插入/删除操作 . 注意# - 这使得该表成为临时表,如果您在使用它之后不丢弃它,它将自动清除 . 但是,完成它们后删除临时表是一种好习惯 .
我 really 建议您使用MERGE语句,它比删除和插入更有效 .
谢谢,这可能是一个很好的选择 . 但是,我确实完成了我想要做的事情:)在catch部分中,我从实时数据库表中选择了所有PK到DataReader中 . 然后我循环读取返回的行 . 在每个循环中,我使用MemoryDataTable.rows.find方法检查MemoryDataTable中是否存在DataReader行,如果是,则删除它 .