【问题标题】:Equivalent of ObjectInputStream and ObjectOutputStream in C#C# 中 ObjectInputStream 和 ObjectOutputStream 的等价物
【发布时间】:2016-04-11 00:24:28
【问题描述】:

CSharp 中这些 Java 类的等价物是什么?

它用于实现一个带有套接字的接口。

谢谢

【问题讨论】:

  • 以及相当于 Socket 的方法“getOutputStream()”和“getInputStream()”?

标签: java c# sockets stream


【解决方案1】:

.NET 上有很多可用的序列化程序。

最简单的一种是二进制序列化。它是 C# 中最相似的等价物

https://msdn.microsoft.com/en-us/library/4abbf6k0(v=vs.110).aspx

这样做的问题是,如果您使用它,您的服务器和客户端将需要同步升级(即,如果您升级服务器,则必须更新所有客户端,否则服务器将无法反序列化来自旧客户端的请求)

DataContractSerializer 提供 XML 格式的消息,并具有专为 Web 服务设计的选项,因此它可以做一些版本容错。

https://msdn.microsoft.com/en-us/library/system.runtime.serialization.datacontractserializer(v=vs.110).aspx

特别是,它允许丢失属性(例如,当服务器升级以允许更多旋钮,但旧客户端不发送它们时)。

关于您的另一个问题。 要从 Socket 获取流,只需创建一个 System.Net.Socket.NetworkStream 对象实例,并将该套接字作为参数。

Stream s = new NetworkStream(socket);

Windows Communication Foundation (WCF) 抽象出很多关于分布式系统编程的细节。使用 WCF 编写服务器客户端应用程序比使用原始套接字要容易得多。

【讨论】:

  • 谢谢!什么是它的等价物“ in = new ObjectInputStream(new BufferedInputStream(sock.getInputStream())); ”以便在套接字中写入?
  • 它在 C# 中不起作用 您创建一个 NetworkStream 对象实例,然后使用 Serializer 对象写入该流。它更像 in = new ObjectInputStream(new BufferedInputStream(sock.getInputStream()); in.writeObject(objectToWrite); 将转换为 NetworkStream ns = new NetworkStream(sock); BinaryFormatter bf = new BinaryFormatter(); bf.Serialize( objectToWrite, ns);
【解决方案2】:

没有直接的等价物,但是使用普通的 Stream 和 XmlSerializer/BinaryFormatter 很容易实现它的功能。

这是一个使用 XmlSerializer 的示例:

public void StoreToFile<T>(T ObjectToStore, string FileName)
{
    XmlSerializer ser = new XmlSerializer(typeof(T));
    using(Stream str = File.Create(FileName))
        ser.Serialize(str, ObjectToStore);
}

public T RetrieveFromFile(string FileName)
{
    XmlSerializer ser = new XmlSerializer(typeof(T));
    using(Stream str = File.Open(FileName))
        return (T)ser.Deserialize(str);
}

然后,当你想在文件中存储一个类时:

MyClass instance = new MyClass(); //The class we want to store.
StoreToFile(instance, "instance.dat");

然后检索它:

MyClass instance = RetrieveFromFile<MyClass>("instance.dat");

这是一个在文件中仅存储一个类的基本示例,但您可以对其进行扩展以存储连接到这些流上的更多项目。

此外,getOutputStream 和 getInputStream 没有直接对应物,您始终可以使用 NetworkStream:

NetworkStream myStream = new NetworkStream(theSocket);

它将表现为输入和输出流,在 .net 中流通常是读/写的,因此不需要两个分离的流。

【讨论】:

    【解决方案3】:

    同样可以使用 JSON 序列化来完成,例如:

        private StreamReader inputStream = ...;
        private StreamWriter outputStream = ...;
                
         public void writeObject<T>(T s)
         {
              if (outputStream != null)
              { string jsonString = JsonSerializer.Serialize<T>(s);
                outputStream.WriteLine(jsonString); 
              }
              else
              { Console.WriteLine("ERROR: null output stream!");  }
         }
    
            public T readObject<T>()
            { if (inputStream != null)
              {
                string jsonString = inputStream.ReadLine();
                T res =
                  JsonSerializer.Deserialize<T>(jsonString);
                return res;
              }
              return default(T); 
            }
    

    注意T 必须是公共类,并且只有公共字段会被序列化。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2012-05-29
      • 2015-01-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-04-02
      相关资源
      最近更新 更多