新闻中心

C#怎么比较两个对象是否相等 Equals和GetHashCode重写方法

2025-12-15
浏览次数:
返回列表
必须同时重写Equals和GetHashCode,因为哈希容器依赖二者协同工作:相等对象的GetHashCode必须相同,Equals用于最终确认;若只重写Equals,可能导致字典中无法查找对象。

c#怎么比较两个对象是否相等 equals和gethashcode重写方法

在C#中,判断两个对象是否“逻辑相等”,不能只靠 == 或默认的 Equals()——尤其是自定义类。关键在于正确重写 Equals(object)GetHashCode(),二者必须成对出现、逻辑一致。否则可能在字典、哈希集里出错,或让相等判断结果不符合预期。

为什么必须同时重写 Equals 和 GetHashCode

这两个方法是 .NET 哈希容器(如 Dictionary<tkey tvalue></tkey>HashSet<t></t>)正常工作的基础:

  • GetHashCode() 用于快速分桶:如果两个对象相等,它们的哈希码 必须相同
  • Equals() 用于精确比对:哈希码相同只是“可能相等”,最终靠 Equals() 确认
  • 反之,如果 GetHashCode() 不一致,Equals() 根本不会被调用(直接判为不等)
  • 若只重写 Equals() 而忽略 GetHashCode(),对象放进 Dictionary 后可能查不到自己

重写 Equals 的基本步骤

以一个简单 Person 类为例,按规范重写 Equals(object obj)

MCP市场 MCP市场

中文MCP工具聚合与分发平台

MCP市场 211 查看详情 MCP市场
  • 先检查 obj 是否为 null 或类型不匹配(用 obj is Person other 最简洁)
  • 比较所有参与逻辑相等判断的字段(通常是 publicprivate 的值型/引用型字段)
  • 对引用类型字段,用 Equals(a, b)(静态方法,可安全处理 null
  • 对值类型字段,直接用 == 即可
  • 如果类有继承关系,需调用基类 base.Equals(obj)
示例:
public override bool Equals(object obj) {
    if (obj is Person other) {
        return Id == other.Id && 
               string.Equals(Name, other.Name, StringComparison.Ordinal) &&
               BirthDate == other.BirthDate;
    }
    return false;
}

重写 GetHashCode 的要点

哈希码不要求唯一,但要求:相等的对象必须返回相同哈希码;尽量让不等对象哈希码分布均匀(减少哈希冲突):

  • 只基于 Equals 中用到的那些字段计算哈希
  • 避免使用可变字段(如后续会修改的属性),否则对象加入哈希集合后修改字段,哈希码变化 → 查找失败
  • C# 9+ 推荐用元组解构简化写法:return (Id, Name, BirthDate).GetHashCode();
  • 老版本可用 HashCode.Combine(Id, Name, BirthDate)(.NET Core 2.1+)或手动组合(如 Id.GetHashCode() ^ (Name?.GetHashCode() ?? 0) )
示例:
public override int GetHashCode() {
    return (Id, Name, BirthDate).GetHashCode();
}

额外建议和常见坑

  • 考虑实现 IEquatable<t></t> 接口,提供类型安全的 Equals(T other),避免装箱,性能更好
  • 重载 ==!= 运算符时,内部应调用 Equals(),保持语义一致
  • 记录类型(record)自动实现结构相等和哈希,适合不可变数据场景
  • 如果类是可变的,且字段可能被修改,务必确保修改不涉及参与 Equals 判断的字段,否则哈希容器行为不可预测

基本上就这些。核心就一条:Equals 怎么比,GetHashCode 就怎么算——不多不少,不变不乱。

以上就是C#怎么比较两个对象是否相等 Equals和GetHashCode重写方法的详细内容,更多请关注其它相关文章!


# .net  # 为什么  # 重写  # 如何使用  # 如何实现  # 怎么处理  # c#  # 网站营销推广ppt  # 漳州网站建设要多久完成  # 汉中营销推广哪家好  # 巩义百度网站推广  # 南充网站优化收费平台  # 郑州需要网站建设的公司  # 锦州品牌推广营销公司  # 武汉营销推广文案朋友圈  # 深圳宝安展示型网站建设  # 推广软文营销平台  # 中文网  # 这两个  # 相关文章  # 能在  # 不多不少  # 尤其是 


相关栏目: 【 科技资讯46185 】 【 网络学院92790


相关推荐: sublime怎么进行远程开发编辑_配置rsub/rmate实现sublime编辑服务器文件  在Qt QML中通过Python字典动态更新TextEdit内容的教程  Win10系统怎么查看已安装更新_Win10卸载有问题的更新补丁  2025AO3夸克浏览器通道_AO3手机HTTPS安全入口分享  NetBeans Ant项目:自动化将资源文件复制到dist目录的教程  163邮箱网页版入口导航平台 163邮箱网页版登录入口官网导航  为什么简单的XML文件也会解析失败? 检查隐藏的非打印字符(如BOM)的方法  C++如何比较两个字符串_C++ string compare函数与操作符对比  中兴BladeV30怎样用测距估书架层高_iPhone中兴BladeV30测距估书架层高【家装参考】  谷歌浏览器如何快速清除某个网站的数据_Chrome网站缓存清理方法  生成rdflib自定义SPARQL函数:参数匹配与实践指南  J*aScriptWebpack优化_J*aScript构建工具实战  MAC怎么在地图App里使用“四处看看”_MAC体验部分城市的3D实景街景  打开就能玩的植物大战僵尸 植物大战僵尸网页版传送门  c++如何使用Meson构建系统_c++比CMake更快的构建工具  Sublime Text怎么设置垂直标尺_Sublime配置Rulers规范代码长度  J*a最大堆Heapify方法修复:索引计算与边界条件深度解析  汽水音乐车机版横屏版7.1 汽水音乐车机版横屏版下载入口  如何在J*a中使用Locale处理多语言环境  LINQ to XML为何解析失败? 深入理解C# XDocument的异常处理  C++ typeid如何获取类型信息_C++ RTTI运行时类型识别用法  抖音极速版最新版本 抖音极速版官方下载地址  抖音未来赚钱的新趋势 2025年值得关注的变现风口分析  sublime如何只显示或隐藏特定类型文件_sublime侧边栏文件过滤  印象笔记怎样用批量导出备知识库_印象笔记用批量导出备知识库【备份方法】  照顾宝贝2小游戏免费秒玩入口  CSS子选择器:如何区分并样式化嵌套列表的子层级  顺丰国际快递查询 国际件官方查询入口  Yandex官网搜索引擎免登录_俄罗斯Yandex一键直达入口  Excel如何用迷你图显趋势_Excel用迷你图显趋势【趋势小图】  蛙漫2日版入口 WAMAN2(日版)无删减漫画官网链接  C++ map遍历方法大全_C++ map迭代器使用总结  J*aScript中高效清空DOM列表元素:解决for循环中断与任务管理问题  聚水潭ERP登录页面入口 聚水潭ERP官网登录界面  QQ邮箱在线登录平台 QQ邮箱个人邮箱网页版入口  将HTML动态表格多行数据保存到Google Sheet的教程  小米Civi 4录制视频过暗_小米Civi 4亮度优化  网易大神账号申诉需要多久_网易大神账号申诉流程说明  win11如何卸载Windows更新补丁 Win11解决更新导致系统不稳定的问题【修复】  Vue.js 图片显示异常排查:理解应用挂载范围与DOM ID唯一性  GemBox Document HTML转PDF垂直文本渲染问题及解决方案  AO3最新入口2025公告_AO3中文官网合集  HTML转PPT成品工具有哪些?HTML网页转PPT成品工具大全  Golang如何使用new_Go new分配内存机制讲解  R星幕后开发视频泄露 包含《GTA6》等多款大作  抖音隐秘迷城小游戏入口_ 抖音冒险解谜小游戏秒玩  支付宝解绑银行卡步骤_支付宝如何解除绑定银行卡  特斯拉自动驾驶房车计划曝光 原型车将于2027年亮相  在J*a中如何捕获IndexOutOfBoundsException_索引越界异常防护方法说明  steam官方网页快速访问 steam账号注册全流程 

搜索