使用For Each遍历DataGridView列遇异常,求替代方案及List转换方法
问题解答
a) 改用List的思路是否正确?
完全正确。For Each循环直接遍历DataGridViewColumnCollection时,修改列的Visible属性可能触发DataGridView内部的集合变更(比如首次加载时的布局调整、事件触发导致的集合元素状态变化),打破枚举的稳定性,从而抛出"Collection was modified"异常。将列集合复制到独立的List后,遍历的是副本,修改原集合的操作不会影响枚举过程,从根源避免了冲突。
b) 如何将列集合转换为List?
在VB.NET中,DataGridViewColumnCollection实现的是非泛型IEnumerable,需要先通过Cast(Of DataGridViewColumn)转换为泛型集合,再生成List。代码示例如下:
' 将列集合转换为List副本 Dim columnsList As List(Of DataGridViewColumn) = dgv.Columns.Cast(Of DataGridViewColumn).ToList() ' 遍历List设置列显示/隐藏 For Each dtc As DataGridViewColumn In columnsList Select Case dtc.Name Case "ColumnName1", "ColumnName2", "ColumnName3" dtc.Visible = True Case Else dtc.Visible = False End Select Next
也可直接通过List构造函数创建副本:
Dim columnsList As New List(Of DataGridViewColumn)(dgv.Columns.Cast(Of DataGridViewColumn))
关于异常仅首次出现的说明
首次执行时DataGridView处于初始化阶段,修改列可见性会触发更多内部布局或集合调整逻辑,导致集合被修改;后续操作时控件已完成初始化,相关内部变更不再触发集合枚举冲突,因此无报错。另一个DataGridView无异常可能是因为初始化状态、绑定时机或控件属性设置不同,规避了首次遍历的集合变更问题。
内容的提问来源于stack exchange,提问作者Alan O'Brien
相关产品推荐
相关产品推荐

