You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C#中List<int[]>元素移除失败:数独求解器开发问题

数独求解器中List<int[]>移除元素失效的问题与解决方案

为什么Remove方法无效?

int[]是引用类型,List.Remove(T item)默认用引用相等性判断:只有传入的数组对象和列表里的某个数组是同一个内存引用时,才会被移除。你新创建的new int[] {1,7}和列表里的new int[] {1,7}是两个完全独立的对象,内存地址不一样,所以Remove找不到要删除的元素。

解决方法

方法1:用RemoveAll按数组内容匹配删除

RemoveAll支持传入条件判断逻辑,遍历列表把符合条件的元素全部移除。针对你的场景,直接判断数组的列、行值是否匹配:

List<int[]> test1 = new List<int[]>();
test1.Add(new int[] { 0, 0 });
test1.Add(new int[] { 1, 7 });

// 移除列=1、行=7的空白格位置
test1.RemoveAll(arr => arr[0] == 1 && arr[1] == 7);

方法2:改用值类型存储位置(更推荐)

引用类型的相等性问题是天生的,换成值类型就能直接按内容判断相等,还能提升代码可读性。推荐两种选择:

方案A:用ValueTuple(C#7.0+支持)

轻量无需自定义类型,还能给字段命名:

// 用(列, 行)的元组存储位置
List<(int Col, int Row)> emptyCells = new List<(int, int)>();
emptyCells.Add((0, 0));
emptyCells.Add((1, 7));

// 直接按内容移除,值类型默认按内容判断相等
emptyCells.Remove((1, 7));

方案B:自定义结构体

如果需要更强的可读性或后续扩展属性,自定义结构体是更好的选择:

public struct CellPosition
{
    public int Column { get; set; }
    public int Row { get; set; }

    // 重写Equals和GetHashCode,确保按内容判断相等
    public override bool Equals(object obj)
    {
        return obj is CellPosition pos &&
               Column == pos.Column &&
               Row == pos.Row;
    }

    public override int GetHashCode()
    {
        return HashCode.Combine(Column, Row);
    }
}

// 使用示例
List<CellPosition> emptyCells = new List<CellPosition>();
emptyCells.Add(new CellPosition { Column = 0, Row = 0 });
emptyCells.Add(new CellPosition { Column = 1, Row = 7 });

emptyCells.Remove(new CellPosition { Column = 1, Row = 7 });

List<int[]>是不是最优方案?

不推荐用List<int[]>,原因有三个:

  1. 可读性差:数组索引0和1到底代表列还是行?过段时间自己都容易搞混
  2. 引用类型的相等性坑:就是你现在遇到的Remove失效问题
  3. 扩展性差:如果后续要给空白格加候选数、标记状态等,数组没法直接扩展属性

用ValueTuple或自定义结构体才是更适合的方案,既解决了相等性问题,又能提升代码的可维护性。

内容的提问来源于stack exchange,提问作者Lisa

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.01 15:31:49