我是一个Java人,并试图在C#中实现一些代码。我做了一个小时的研究,但找不到任何。 我有一个我声称为Generic的接口叫
interface TypeSerializer<T>
然后我有两个这样的实现。
class StringSerializer: TypeSerializer<String>
和
class ByteArraySerializer: TypeSerializer<byte[]>
现在我想创建一个包含这些实例的数组,并将数组引用为TypeSerializer。是这样的:
TypeSerializer[] serializers =
new TypeSerializer[2] {new ByteArraySerializer(), new StringSerializer()};
此代码无法编译,但在Java中,类似的代码会编译。
我也试过了......
TypeSerializer<Object>[] serializers =
new TypeSerializer<Object>[2] {new ByteArraySerializer(), new StringSerializer()};
仍然没有办法。
如何在不知道通用类型的情况下声明此数组并访问实例。
修改
基于下面的答案,很明显我应该有两个接口;有和没有通用。 这是接口方法。你能否告诉我们如何实施它们。
public interface ITypeSerializer<T>:TypeSerializer
{
void write(BinaryWriter writer, T obj);
T read(BinaryReader reader);
}
答案 0 :(得分:5)
您可以创建泛型版继承的接口的非泛型版本,这会像往常一样强制实现类。
interface ITypeSerializer { }
interface ITypeSerializer<T> : ITypeSerializer { }
class StringSerializer : ITypeSerializer<string> { } // implements ITypeSerializer, too
// non-generic array
ITypeSerializer[] serializers = ...
ITypeSerializer
上需要的任何方法都应接受或返回object
,其实现通常是泛型版本的传递方法。
一个实现示例:
public interface ITypeSerializer
{
void Write(BinaryWriter writer, object obj);
object Read(BinaryReader reader);
}
public interface ITypeSerializer<T> : ITypeSerializer
{
void Write(BinaryWriter writer, T obj);
T Read(BinaryReader reader);
}
实施ITypeSerializer<T>
时,还需要提供ITypeSerializer
方法的实现。一种常见的模式是显式地实现泛型和非泛型,这样非泛型方法只有在通过接口引用类时才可见。
class StringSerializer : ITypeSerializer<string>
{
// implicit implementation of ITypeSerializer<string>
public void Write(BinaryWriter writer, string obj)
{
// provide core implementation here
}
public string Read(BinaryReader reader)
{
// provide core implementation here
}
// explicit implementation of ITypeSerializer
void ITypeSerializer.Write(BinaryWriter writer, object obj)
{
if (!(obj is string)) throw new ArgumentException("obj");
this.Write(writer, (string)obj);
}
object ITypeSerializer.Read(BinaryReader reader)
{
return this.Read(reader);
}
}
注意非泛型方法是如何简单地传递给通用对应方的。
答案 1 :(得分:2)
您的界面可以这样声明:
interface TypeSerializer<out T>
“out”使您使用C#的通用方差功能,并且您将能够编译您尝试过的第二个表单:
TypeSerializer<Object>[] serializers =
new TypeSerializer<Object>[2] {new ByteArraySerializer(), new StringSerializer()};
这适用于C#4.0及更高版本
答案 2 :(得分:1)
如果您不了解泛型类型,则使用通用接口并不理想。我很想使用:
interface ITypeSerializer {...}
使用与object
一起使用的API。在大多数情况下,这不会出现问题 - 因为您最有可能序列化类(因此没有装箱)。偶尔演员不会成为一个问题。
如果你真的想要,你可以拥有双通用/非通用API,但除非你需要它,这可能是一种过度杀戮(说有人花了 很多 时间与这个确切的场景非常相似)。
答案 3 :(得分:0)
这应该可以解决问题:
interface ITypeSerializer { }
interface ITypeSerializer<T> : ITypeSerializer { }
请注意,命名以大写I