我想创建一个只适用于具有Serializable
属性的类的泛型方法,例如
public static int Foo<T>(T obj) where T : Serializable {
...
}
但显然上面没有编译。而且我猜我是否将SerializableAttribute
放在那里,它会坚持T
是属性,而不是具有该属性的类。
你怎么做这样的事情?
答案 0 :(得分:4)
无法对属性进行约束。一种解决方案可能是使用反射来分析传递给方法的对象,并查看它是否声明了Serializable
属性。
答案 1 :(得分:2)
您可以实现ISerializable接口并使用“where T:ISerializable”,但是您必须在每个类中实现ISerializable方法。运行时检查可以在类上查找SerializableAttribute,但是您没有编译时检查。您可以考虑编写自己的接口,这些接口几乎不需要实现,可能只是一个Property并在每个类上实现该接口。有点像...
public interface ISerializableSet {
bool IsSerializable { get; }
}
您的实现可以使用反射然后进行运行时检查,您的Foo方法将被声明为“where T:ISerializableSet”用于编译时检查。
这是一个更完整的例子......
public interface ISerializableSet
{
bool IsSerializable { get; }
}
[Serializable]
class SerializableClass : ISerializableSet
{
[NonSerialized]
private bool _runTimeCheck = true;
#region ISerializableSet Members
public bool IsSerializable
{
get {
if(!_runTimeCheck)
return true;
if(0 != (this.GetType().Attributes & System.Reflection.TypeAttributes.Serializable))
return true;
return false;
}
}
#endregion
}
public static class Bar2
{
public static int Foo<T>(T obj) where T : ISerializableSet
{
ISerializableSet sc = obj;
Console.WriteLine("{0}", sc.IsSerializable.ToString());
return 1;
}
}
您可以在构造函数中测试IsSerializable属性并抛出运行时异常,以防有人无意中删除[Serializable]。如果您正在使用单元测试,则可以在测试时检测到问题。
答案 2 :(得分:0)
您必须使该类实现一个接口应用该属性。 然后,您可以通过界面进行过滤:
public static int Foo<T>(T obj) where T : ISerializable
{}