c# - 使用 protobuf-net 序列化 C# 字符串时出错

标签 c# sockets serialization protobuf-net

我想编写一个 C# 客户端通过 protobuf-net 将字符串发送到 TCP 服务器(已实现)。但是,当我尝试使用 protobuf-net 序列化字符串时,我得到了 TypeInitializerException “'Singleton' 的类型初始化程序引发了异常。”

这是代码:

public static void TelnetConnect(string host, int port) {
    ...
    Message msg = new Message("This is a test.");
    byte[] sentbytes = msg.Serialize();
    ...
}

[ProtoContract]
public abstract class MessageI {
    public byte[] Serialize() {
        byte[] result;
        using (var stream = new MemoryStream()) {
            Serializer.Serialize(stream, this);  //THIS LINE THROWS EXCEPTION
            result = stream.ToArray();
        }
        return result;
    }
}

[ProtoContract]
public class Message : MessageI {
    [ProtoMember(1)]
    public string str { get; set; }

    public Message(string s) {
        this.str = s;
    }
}

我尝试了该站点和其他站点建议的多种方法,但均未成功。我在 Visual Studio 2010 上使用 C#。

谢谢,非常感谢您的帮助。

更新:堆栈跟踪是:
   at ProtoBuf.Meta.RuntimeTypeModel.get_Default()
   at ProtoBuf.Serializer.Serialize[T](Stream destination, T instance)
   at PingNorbertServer.MessageI.Serialize() in C:\Users\RS88517\Documents\Visual Studio 2010\Projects\PingNorbertServer\PingNorbertServer\NorbertClient.cs:line 37
   at PingNorbertServer.NorbertClient.TelnetConnect(String host, Int32 port) in C:\Users\RS88517\Documents\Visual Studio 2010\Projects\PingNorbertServer\PingNorbertServer\NorbertClient.cs:line 23
   at PingNorbertServer.NorbertClient.Main(String[] args) in C:\Users\RS88517\Documents\Visual Studio 2010\Projects\PingNorbertServer\PingNorbertServer\NorbertClient.cs:line 14
   at System.AppDomain._nExecuteAssembly(RuntimeAssembly assembly, String[] args)
   at System.AppDomain.ExecuteAssembly(String assemblyFile, Evidence assemblySecurity, String[] args)
   at Microsoft.VisualStudio.HostingProcess.HostProc.RunUsersAssembly()
   at System.Threading.ThreadHelper.ThreadStart_Context(Object state)
   at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean ignoreSyncCtx)
   at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
   at System.Threading.ThreadHelper.ThreadStart()

最佳答案

我无法重现错误;您的代码,直接复制,工作正常:

static void Main()
{
    var data = new Message("abc").Serialize();
}

但是,要尝试提供帮助:
  • 第一,catch Exception ,然后查看 .InnerException .大多数异常(exception)情况都有更多信息;例如:
    try {
        // HERE: the code that errors
    } catch(Exception ex) {
        while(ex != null) {
            Console.Error.WriteLine(ex.Message);
            ex = ex.InnerException;
        }
        throw;
    }
    
  • 其次,请注意继承模型的一个常见问题是不声明继承 - 看看基类是否需要装饰,例如:
    [ProtoInclude(1, typeof(Message))]
    
  • 另一个观察结果是缺少公共(public)无参数构造函数;现在,protobuf-net 不再坚持这一点(实际上,它看起来将问题中的代码视为“自动元组”,并使用存在的构造函数),但您也可以提供额外的(可能是非公共(public)的)无参数构造函数:
    private Message() {}
    

    或告诉它完全跳过构造函数:
    [ProtoContract(SkipConstructor = true)]
    

  • 但是:在不知道异常消息是什么的情况下,很难进一步推测。

    关于c# - 使用 protobuf-net 序列化 C# 字符串时出错,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21469868/

    相关文章:

    c++ - Linux套接字编程测试

    jquery - 我可以将数据添加到已经序列化的数组中吗?

    c# - MAUI.NET 在按下后退按钮时显示弹出窗口

    c# - 如何让 CLR 知道从 GAC 选择哪个程序集?

    c# - Unity 记录静态方法 AOP 风格或无接口(interface)

    android - SSL证书安卓

    sockets - 原始套接字接收缓冲区

    c++ - 将 uint8_t 转换为其二进制表示

    c++ - 有没有办法将枚举自动序列化为 int?

    c# - 远程端身份验证失败(流可能仍可用于其他身份验证尝试)