如何修改DataGrid选择事件实现保留最后选中项避免误删?
DataGrid多选删除与防误删实现方案
问题分析
你之前移除if (rs != null)后未能清空选中ID,是因为当无选中项时dg.SelectedItem为null,rs也为null,执行rs["ID"].ToString()会触发空引用异常,代码中断,无法完成赋值操作。同时原代码仅支持单条删除,也未处理取消选中后的误删风险。
修改后代码
首先在类中添加存储选中ID的集合字段:
// 存储选中的客户ID列表 private List<string> _selectedCustomerIds = new List<string>();
然后修改SelectionChanged事件,支持多选ID收集,并正确处理无选中项的情况:
private void customersGrid_SelectionChanged(object sender, SelectionChangedEventArgs e) { DataGrid dg = (DataGrid)sender; _selectedCustomerIds.Clear(); // 遍历所有选中项,提取ID foreach (var item in dg.SelectedItems) { if (item is DataRowView rs) { string id = rs["ID"].ToString(); if (!string.IsNullOrEmpty(id)) { _selectedCustomerIds.Add(id); } } } }
最后修改删除按钮点击事件,支持批量删除并避免误删:
private void btnDelete_Click(object sender, RoutedEventArgs e) { // 无选中项时直接提示,避免误删 if (_selectedCustomerIds.Count == 0) { MessageBox.Show("请先选择要删除的客户", "提示", MessageBoxButton.OK, MessageBoxImage.Information); return; } if (MessageBox.Show($"确定要删除选中的{_selectedCustomerIds.Count}条记录吗?", "确认删除", MessageBoxButton.YesNo, MessageBoxImage.Question) == MessageBoxResult.Yes) { using (var connection = new SqlConnection(_connectionString)) { connection.Open(); // 构造批量删除的参数化SQL,避免SQL注入 string paramPlaceholders = string.Join(",", _selectedCustomerIds.Select((_, idx) => $"@id{idx}")); string deleteSql = $"DELETE FROM Customers WHERE ID IN ({paramPlaceholders})"; using (var command = new SqlCommand(deleteSql, connection)) { // 绑定参数 for (int i = 0; i < _selectedCustomerIds.Count; i++) { command.Parameters.AddWithValue($"@id{i}", _selectedCustomerIds[i]); } int deletedCount = command.ExecuteNonQuery(); MessageBox.Show($"成功删除{deletedCount}条记录", "删除完成", MessageBoxButton.OK, MessageBoxImage.Information); GetCustomersFromDataBase(); _selectedCustomerIds.Clear(); } } } }
关键改进点
- 改用集合存储选中ID,天然支持多选删除
- 取消选中时清空集合,点击删除按钮会先判断集合是否为空,彻底避免误删
- 使用参数化SQL查询,解决原代码的SQL注入风险
- 遍历
SelectedItems而非仅取SelectedItem,适配多选场景
内容的提问来源于stack exchange,提问作者ApathyErr
相关产品推荐
相关产品推荐

