Gli*_*kot 5 c# generics argument-passing
我第一次涉足仿制药,并对它们有所了解.我有一个方法,旨在接受任何对象的两个列表,匹配它们各种方式并返回匹配/不匹配的对象(方法内的东西可能不是这里的关键).目的是接受任何类型的对象,无论是客户还是其他任何对象.然而,我已经遇到了让它接受'字符串'的问题,我猜是因为它没有使用new()关键字进行初始化,并且不像普通的实例类.
所以,我有一个像这样的方法声明:
public static compareResult<T> stepCompare<T>(List<T> leftList, List<T> rightList, Comparison<T> IDComparer = null, Comparison<T> lowLevelComparer = null, bool confirmUniqueness = true) where T : IComparable, new()
Run Code Online (Sandbox Code Playgroud)
不可否认,在最后添加where子句是为了响应错误"无法创建变量类型'T'的实例,因为它没有new()约束".这出现在方法中的一条线上
T lastItem = new T();
Run Code Online (Sandbox Code Playgroud)
但是,现在,如果我试图将其传递两次Lists<string>
,它会说" 'string' must be a non-abstract type with a public parameterless constructor in order to use it as parameter 'T' in the generic type or method 'MF.Comparers.stepCompare<T>(System.Collections.Generic.List<T>, System.Collections.Generic.List<T>, System.Comparison<T>, System.Comparison<T>, bool)'
......
任何让这个方法接受的方法都列出了它们是字符串还是其他类?或者将字符串列表放入将被接受的类型的快捷方式?
你不能string
满足new()
约束,不.虽然string
是普通类,并且可以使用构造函数以完全正常的方式创建实例,但它没有无参数构造函数.
最好的方法实际上取决于你为什么要有这样的代码行,包括lastItem
.如果您只想要一些默认值,那么default(T)
可能是最好的方法.
如果你真的不想要创建的新实例T
,那么你或许应该接受一个Func<T>
在方法的参数列表,如按需创建一个默认值的一种方式.或者,如果您对使用特定单个值作为默认值感到满意,则只需添加类型参数即可T
.没有看到你的其余代码就很难说.
如果你想要任何物体,你可能不需要生活new T()
.您可以使用反射,特殊情况(string
等)的组合来做同样的事情Activator.CreateInstance<T>()
- 然而,IMO您应该限制自己(在这种情况下)default(T)
,对于引用类型(包括字符串)和可空值,它将为null类型,以及非可空值类型的全零.除了满足编译器的明确赋值规则之外,您还应该使用bool
或类似的以确保实际上不使用该值.