C#怎么使用协变和逆变 C#泛型中的in和out关键字协变逆变是什么意思怎么用【语法】

协变(out)和逆变(in)仅适用于接口和委托,协变允许更具体的类型赋给更宽泛的类型变量,仅限返回值、get访问器等输出位置;逆变则用于输入位置如方法参数,仅限接口和委托;类不支持协变或逆变。协变(out)只适用于接口和委托,且只能用在输出位置协变允许你把更具体的类型赋给更宽泛的类型变量,比如 IEnumerable<string> 能赋给 IEnumerable<object>。但这不是所有泛型都支持------只有标记了 out 的类型参数才允许协变,而且它**只能出现在返回值、属性 get 访问器、方法返回类型中**,不能出现在参数、字段或 set 访问器里。常见错误现象:void Add(T item) 里用了 out T,编译直接报错 CS1961:"类型参数 T 具有无效的方差"。IEnumerable<T>、IComparer<out T>、Func<out T> 是典型协变接口/委托自定义接口要协变,必须显式写 interface IProducer<out T>,且所有 T 出现位置都得是"只读"的类不支持协变或逆变------class List<out T> 是非法语法逆变(in)只用于输入位置,且仅限接口和委托逆变让你把更宽泛的类型传给更具体的期望,比如 Action<object> 可以赋给 Action<string>(因为 string 是 object 的子类,而 Action 只消费参数,不返回它)。逆变的关键是:类型参数只能出现在**参数位置**,不能用于返回值或属性 get。使用场景:当你需要一个"能处理任意父类的委托",但实际只想传子类实例时,逆变就省去了手动包装。Action<in T>、IComparer<in T>、Predicate<in T> 是典型逆变接口/委托错误写法:T GetFirst() 出现在 interface IConsumer<in T> 里 → 编译失败 CS1961注意 IComparer<T> 同时支持 in 和 out?不对。.NET 中它是 IComparer<in T>,因为比较逻辑只接收两个 T 参数,不返回 T泛型类永远不支持 in/out,别试了你没法给 class Box<T> 加 in 或 out。C# 语言规范明确禁止------类的类型参数必须是不变的(invariant)。这是因为类既有输入(构造函数、方法参数),又有输出(属性、返回值),无法统一满足协变或逆变约束。 Tellers AI Tellers是一款自动视频编辑工具,可以将文本、文章或故事转换为视频。

相关推荐
2603_965148115 小时前
如何解析JSON数据?API返回的商品信息处理教程
开发语言·数据库·python·自动化·json·api
ltl5 小时前
RocksDB 经典故障排查:L0、compaction 与 write stall
数据库
xfhuangfu6 小时前
Oracle中建立到CDB和PDB的连接
数据库·oracle·rpc
小小龙学IT6 小时前
DuckDB 深度实战:用 C++ 在进程内跑一个「分析型数据库」
数据库·c++
jufeng13076 小时前
【系列:手搓自主 AI Agent:Hermes 架构原理剖析 · 第 8 篇】
python·ai agent·配置系统
NineData6 小时前
DTCC 2026 预告|NineData CEO& 创始人叶正盛:面向 AI Agent 的数据库 DevOps 与数据复制实践
数据库·人工智能·数据库开发·devops·ninedata·数据库技术·dtcc
circuitsosk6 小时前
跨境电商智能化实战:AI如何赋能客服自动回复、广告智能投放与供应链预测
大数据·人工智能·python·langchain·智能客服
J_bean7 小时前
MySQL 事务是否必须手动开启?
数据库·mysql·数据库事务·自动提交·手动提交
J_bean7 小时前
MySQL InnoDB 如何检测死锁、判定死锁、处理死锁
数据库·mysql·死锁·死锁检测·处理死锁·死锁判定
2601_956319887 小时前
2026年零基础学量化:从看懂示例到写清条件和动作
人工智能·python