Pergunta

eu tenho um DateRange objeto que representa a noção de Infinito via referência estática conforme mostrado abaixo.Como você pode ver, os pontos finais que definem o Infinity também são referências estáticas em uma classe diferente, DatePoint.Past e DatePoint.Future.

Agora preciso serializar isso (como parte de um método Clone profundo que usa serialização) e saber quando é desserializado que uma instância com DateTime.Min e DateTime.Max como endpoints, então a instância deve ser DateRange.Infinity.Então eu acho que preciso fazer isso ISerializable.

Minha primeira tentativa de implementação ISerializable é bastante pobre;e mas estou mostrando isso na esperança de sugerir uma solução mais rápida para alguém.Eu usei um código semelhante para o NHibernate armazenar DateRange no banco de dados e reconstituir o Infinity, mas ainda não estou conseguindo aplicar isso para serialização.

DatePoint é marcado [Serializable] mas não implementa ISerializable.

pergunta editada

Não estou procurando serializar/desserializar o Infinity.O que eu sou procurando é um gancho para onde posso levar o desserializado DataRange e decida se é equivalente a Infinity.

**

Saúde, Berryl

Intervalo de datas

[Serializable]
[TypeConverter(typeof(DateRangeTypeConverter))]
public class DateRange : ValueObject, IRange<DatePoint, DateRange, TimeSpan>, ISerializable
{
    /// <summary>
    /// Returns a range spanning <see cref="DatePoint.Past"/> and <see cref="DatePoint.Future"/>.
    /// </summary>
    public static readonly DateRange Infinity = new DateRange(DatePoint.Past, DatePoint.Future);


    /// <summary> The start of the <see cref="DateRange"/> range. </summary>
    public DatePoint Start { get; protected set; }

    /// <summary> The end of the <see cref="DateRange"/> range. </summary>
    public DatePoint End { get; protected set; }

}

Ponto de data

public class DatePoint : ValueObject, IComparable<DatePoint>, IComparable<DateTime>, IComparable, IEquatable<DatePoint>, IEquatable<DateTime>, IFormattable
{

    /// <summary>The undefined infinite past, smaller than any other date except itself.</summary>
    public readonly static DatePoint Past = DateTime.MinValue;

    /// <summary>The undefined infinite future, larger than any other date except itself.</summary>
    public readonly static DatePoint Future = DateTime.MaxValue;

}

Primeira tentativa ISerializable

    protected DateRange(SerializationInfo info, StreamingContext ctx) {
        if (info == null)
            throw new System.ArgumentNullException("info");
        var start = (DatePoint)info.GetValue("Start", typeof(DatePoint));
        var end = (DatePoint)info.GetValue("End", typeof(DatePoint));
        // its Infinity if so
        if((start.Equals(DatePoint.Past) && end.Equals(DatePoint.Future)))
            return;
    }

    public void GetObjectData(SerializationInfo info, StreamingContext context)
    {
    }
Foi útil?

Solução

Você pode implementar IObjectReference e substitua o objeto após a desserialização:

object IObjectReference.GetRealObject(StreamingContext context)
{
    if (Start.Equals(DatePoint.Past) && End.Equals(DatePoint.Future))
    {
        return Infinity;
    }
}

Veja o documentação.

Outras dicas

Você não pode criar uma instância de um membro estático e, portanto, eles não podem ser serializados ou desserializados.

Em vez disso, você pode criar uma propriedade pública adequada com um protected set que não faz nada e um get que retorna o resultado que você deseja.A propriedade pode então ser serializada, mas não desserializada porque isso seria um exercício de futilidade...

Eu faço NÃO gosto de responder à minha própria pergunta, mas aqui está uma solução que parece funcionar.Provavelmente eu simplesmente não fiz a pergunta certa em primeiro lugar e não sabia como fazer o que está abaixo quando a fiz.

Alguém vê uma maneira melhor de fazer isso, por favor, diga!

Saúde,
Berryl

Faça DateRange implementar ISerializable

    protected DateRange(SerializationInfo info, StreamingContext context) {
        if (info == null)
            throw new ArgumentNullException("info");

        var foundPast = (bool) info.GetValue("thePast", typeof (bool));
        if (foundPast)
            Start = DatePoint.Past;
        var foundFuture = (bool) info.GetValue("theFuture", typeof (bool));
        if (foundFuture)
            End = DatePoint.Future;
    }

    public void GetObjectData(SerializationInfo info, StreamingContext context)
    {
        info.AddValue("thePast", Start.Equals(DatePoint.Past), typeof(bool));
        info.AddValue("theFuture", End.Equals(DatePoint.Future), typeof(bool));
    }
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top