首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >将具体类转换为泛型基接口

将具体类转换为泛型基接口
EN

Stack Overflow用户
提问于 2009-11-22 14:46:57
回答 3查看 6.9K关注 0票数 2

以下是我面临的场景:

代码语言:javascript
复制
public abstract class Record { }

public abstract class TableRecord : Record { }

public abstract class LookupTableRecord : TableRecord { }

public sealed class UserRecord : LookupTableRecord { }

public abstract class DataAccessLayer<TRecord> : IDataAccessLayer<TRecord>
    where TRecord : Record, new() { }

public abstract class TableDataAccessLayer<TTableRecord> : DataAccessLayer<TTableRecord>, ITableDataAccessLayer<TTableRecord>
    where TTableRecord : TableRecord, new() { }

public abstract class LookupTableDataAccessLayer<TLookupTableRecord> : TableDataAccessLayer<TLookupTableRecord>, ILookupTableDataAccessLayer<TLookupTableRecord>
    where TLookupTableRecord : LookupTableRecord, new() { }

public sealed class UserDataAccessLayer : LookupTableDataAccessLayer<UserRecord> { }

public interface IDataAccessLayer<TRecord>
    where TRecord : Record { }

public interface ITableDataAccessLayer<TTableRecord> : IDataAccessLayer<TTableRecord>
    where TTableRecord : TableRecord { }

public interface ILookupTableDataAccessLayer<TLookupTableRecord> : ITableDataAccessLayer<TLookupTableRecord>
    where TLookupTableRecord : LookupTableRecord { }

现在,当我尝试执行以下强制转换时,它不能编译:

代码语言:javascript
复制
UserDataAccessLayer udal = new UserDataAccessLayer();
            ITableDataAccessLayer<TableRecord> itdal = (ITableDataAccessLayer<TableRecord>)udal;

但是,当我执行以下强制转换时,它编译时没有运行时错误:

代码语言:javascript
复制
UserDataAccessLayer udal = new UserDataAccessLayer();
            ITableDataAccessLayer<UserRecord> itdal = (ITableDataAccessLayer<UserRecord>)udal;

我真的需要使用基本的ITableDataAccessLayer<TableRecord>接口,因为我不知道具体的类型。

希望这篇文章是描述性的,对回答我的问题有足够的帮助。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2009-11-22 15:46:32

您要做的事情在.NET 4.0中是受支持的,但在3.5中不受支持。它被称为generic covariance。在此期间,您可以做的是创建一个名为ITableDataAccessLayer的非泛型接口(在使用T的地方使用类型Object ),并提供显式接口实现。这是.NET中许多泛型类型处理它的方式。

票数 5
EN

Stack Overflow用户

发布于 2009-11-23 01:06:42

实际上,你想要协方差。几分。

首先,理解为什么有时这必须是非法的。以IList为例。假设您有一个IList<Giraffe>,一个长颈鹿列表。你能把它转换成动物的列表吗?不,不安全。是的,长颈鹿的名单是一份动物名单,从这个意义上说,名单上的所有东西都是动物。但是列表是可变的;您可以将一只老虎放入一个动物列表中,但是如果它真的是一个长颈鹿列表,那么这个方法就必须失败。由于这是不安全的,我们不会在C# 4中使IList协变。

其次,如果您对这个主题感兴趣,您可能想要阅读我的一长串博客文章,这些文章是关于如何设计该功能来维护类型安全的。

http://blogs.msdn.com/ericlippert/archive/tags/Covariance+and+Contravariance/default.aspx

第三,仅供参考,我将在接下来的几周内在我的博客上发布我们用来计算接口何时可以安全地协变或逆变的确切规则。

票数 4
EN

Stack Overflow用户

发布于 2009-11-22 15:45:16

这个可以编译吗?

代码语言:javascript
复制
UserDataAccessLayer udal = new UserDataAccessLayer(); 
ITableDataAccessLayer<TTableRecord> itdal = (ITableDataAccessLayer<TTableRecord>)udal;

或者甚至只是

代码语言:javascript
复制
ITableDataAccessLayer<TTableRecord> itdal = new UserDataAccessLayer(); 

由于它是一个通用接口,它可能需要知道它是什么类型?

知道错误消息也会很有帮助。这通常会让我们对这个问题有所了解。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/1778030

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档