4

我正在重载 System.IO BinaryReader 以序列化某些类以用于文件存储目的。我在处理字典之类的项目时没有遇到任何问题,但使用可空类型并没有成功。有可能吗?具体来说,我正在尝试十进制?和字符串?,但任何类型都应该适合我的解决方案。

出于特定的业务原因,我必须进行二进制序列化,因此请将响应限制为仅适用于此的解决方案。

例如...对于读取/写入字节数组,我使用以下方法:

    public byte[] ReadByteArray()
    {
        int len = ReadInt32();
        if (len > 0) return ReadBytes(len);
        if (len < 0) return null;
        return new byte[0];
    }

    public override void Write(byte[] b)
    {
        int len = b.Length;
        Write(len);
        if (len > 0) base.Write(b);
    }
4

2 回答 2

5

您将需要添加某种标志来让读者知道它是否应该读取下一个字节。

public decimal? ReadNullableDecimal()
{
    bool hasValue = ReadBoolean();
    if (hasValue) return ReadDecimal();
    return null;
}

public void Write(decimal? val)
{
    bool hasValue = val.HasValue;
    Write(hasValue)
    if(hasValue)
        Write(val.Value);
}

但是我们可以很聪明地创建一个适用于所有基于结构的类型的通用方法

public Nullable<T> ReadNullable<T>(Func<T> ReadDelegate) where T : struct
{
    bool hasValue = ReadBoolean();
    if (hasValue) return ReadDelegate();
    return null;
}

public void Write<T>(Nullable<T> val) where T : struct
{
    bool hasValue = val.HasValue;
    Write(hasValue)
    if(hasValue)
        Write(val.Value);
}

如果我想使用我的ReadNullable函数来读取 aInt32我会这样称呼它

Int32? nullableInt = customBinaryReader.ReadNullable(customBinaryReader.ReadInt32);

所以它会测试该值是否存在,如果存在,它将调用传入的函数。


编辑:在上面睡觉后,该Write<T>方法可能无法像您期望的那样工作。因为T不是一个定义明确的类型,所以唯一可以支持它的方法是Write(object)Binary writer 不支持开箱即用。ReadNullable<T>仍然可以工作,如果你想使用仍然使用Write<T>,你需要制作val.Value 动态的结果。您需要进行基准测试以查看是否存在任何性能问题。

public void Write<T>(Nullable<T> val) where T : struct
{
    bool hasValue = val.HasValue;
    Write(hasValue)
    if(hasValue)
        Write((dynamic)val.Value);
}
于 2013-07-09T04:59:27.743 回答
-1
public decimal ReadDecimal()
{
    int len = ReadInt32();
    if (len > 0) return base.ReadDecimal();
    if (len < 0) return null;
    return new decimal;
}


public override void WriteDecimal(decimal d)
{
    if (d==null)
        WriteInt32(-1);
    else
    {
        WriteInt32(sizeof(d)); //16
        Write(d);
    }
}
于 2013-07-09T01:43:15.987 回答