#if !NO_RUNTIME using System; using ProtoBuf.Serializers; namespace ProtoBuf.Meta { /// /// Represents an inherited type in a type hierarchy. /// public sealed class SubType { internal sealed class Comparer : System.Collections.IComparer #if !NO_GENERICS , System.Collections.Generic.IComparer #endif { public static readonly Comparer Default = new Comparer(); public int Compare(object x, object y) { return Compare(x as SubType, y as SubType); } public int Compare(SubType x, SubType y) { if (ReferenceEquals(x, y)) return 0; if (x == null) return -1; if (y == null) return 1; return x.FieldNumber.CompareTo(y.FieldNumber); } } private readonly int fieldNumber; /// /// The field-number that is used to encapsulate the data (as a nested /// message) for the derived dype. /// public int FieldNumber { get { return fieldNumber; } } /// /// The sub-type to be considered. /// public MetaType DerivedType { get { return derivedType; } } private readonly MetaType derivedType; /// /// Creates a new SubType instance. /// /// The field-number that is used to encapsulate the data (as a nested /// message) for the derived dype. /// The sub-type to be considered. /// Specific encoding style to use; in particular, Grouped can be used to avoid buffering, but is not the default. public SubType(int fieldNumber, MetaType derivedType, DataFormat format) { if (derivedType == null) throw new ArgumentNullException("derivedType"); if (fieldNumber <= 0) throw new ArgumentOutOfRangeException("fieldNumber"); this.fieldNumber = fieldNumber; this.derivedType = derivedType; this.dataFormat = format; } private readonly DataFormat dataFormat; private IProtoSerializer serializer; internal IProtoSerializer Serializer { get { if (serializer == null) serializer = BuildSerializer(); return serializer; } } private IProtoSerializer BuildSerializer() { // note the caller here is MetaType.BuildSerializer, which already has the sync-lock WireType wireType = WireType.String; if(dataFormat == DataFormat.Group) wireType = WireType.StartGroup; // only one exception IProtoSerializer ser = new SubItemSerializer(derivedType.Type, derivedType.GetKey(false, false), derivedType, false); return new TagDecorator(fieldNumber, wireType, false, ser); } } } #endif