给出以下几类:
public abstract class User<T> where T : Permission
{
public ICollection<T> Permissions { get; set; }
public class Client : User<Permission.Client> { }
public class Admin : User<Permission.Admin> { }
}
public abstract class Permission
{
public class Client : Permission { }
public class Admin : Permission { }
}
您可以创建User<T>.Client
的实例,同时将类型参数传递给User<T>
,而不是该类本身在实现User<T>
中使用的类型。在以下示例中,尽管该类实际上是通过User<T>.Client
实现T
的,但Permission.Admin
是用User<T>
作为Permission.Client
创建的。
var client = new User<Permission.Admin>.Client();
client.Permissions.Add(new Permission.Client());
client.Permissions.Add(new Permission.Admin()); // cannot convert from 'Permission.Admin' to 'Permission.Client'
至少存在一个构建错误,该错误阻止了向Admin
用户添加Client
权限。但是,用法可能会引起误解,因为传递给User<T>
的类型参数似乎是多余的。
问题:是否有一种方法可以创建User<T>.Client
的实例,而不必在T
上指定类型参数User
(例如{{1} })?
下面是完整示例的dotnetfiddle。
答案 0 :(得分:1)
除了每个人在评论中都提到的有关嵌套类的内容之外,如果要让用户权限同时包含客户端和管理员权限,则需要使用Permission类型的集合
public ICollection<Permission> Permissions { get; set; } = new List<Permission>();
这将解决您的示例,但不会使您的代码更易于遵循。
更新: 为什么您的代码不能再像这样:
public class Program
{
public static void Main(string[] args)
{
var client = new ClientUser();
client.Permissions.Add(new ClientPermission());
//This should fail because a client user can't have admin permissions
client.Permissions.Add(new AdminPermission()); // cannot convert from 'AdminPermission' to 'ClientPermission'
}
public abstract class User<T> where T : Permission
{
public ICollection<T> Permissions { get; set; } = new List<T>();
}
public class ClientUser : User<ClientPermission> { }
public class AdminUser : User<AdminPermission> { }
public abstract class Permission
{
}
public class ClientPermission : Permission { }
public class AdminPermission : Permission { }
}