Ejemplo n.º 1
0
        /// <summary>
        /// Provides the actual implementation for serializing a value of type <see cref="T" />.
        /// </summary>
        /// <param name="value">The value to serialize.</param>
        /// <param name="writer">The writer to serialize with.</param>
        protected override void SerializeImplementation(ref T value, IDataWriter writer)
        {
            var members = FormatterUtilities.GetSerializableMembers(typeof(T), this.OverridePolicy ?? writer.Context.Config.SerializationPolicy);

            for (int i = 0; i < members.Length; i++)
            {
                var  member = members[i];
                Type type;
                var  memberValue = FormatterUtilities.GetMemberValue(member, value);

                type = FormatterUtilities.GetContainedType(member);

                var serializer = Serializer.Get(type);

                try
                {
                    serializer.WriteValueWeak(member.Name, memberValue, writer);
                }
                catch (Exception ex)
                {
                    writer.Context.Config.DebugContext.LogException(ex);
                }
            }
        }
        private static void ReplaceAllReferencesInGraph(object graph, object oldReference, object newReference, HashSet <object> processedReferences = null)
        {
            if (processedReferences == null)
            {
                processedReferences = new HashSet <object>(ReferenceEqualityComparer <object> .Default);
            }

            processedReferences.Add(graph);

            if (graph.GetType().IsArray)
            {
                Array array = (Array)graph;

                for (int i = 0; i < array.Length; i++)
                {
                    var value = array.GetValue(i);

                    if (object.ReferenceEquals(value, null))
                    {
                        continue;
                    }

                    if (object.ReferenceEquals(value, oldReference))
                    {
                        array.SetValue(newReference, i);
                        value = newReference;
                    }

                    if (!processedReferences.Contains(value))
                    {
                        ReplaceAllReferencesInGraph(value, oldReference, newReference, processedReferences);
                    }
                }
            }
            else
            {
                var members = FormatterUtilities.GetSerializableMembers(graph.GetType(), SerializationPolicies.Everything);

                for (int i = 0; i < members.Length; i++)
                {
                    FieldInfo field = (FieldInfo)members[i];

                    if (field.FieldType.IsPrimitive || field.FieldType == typeof(SerializationData) || field.FieldType == typeof(string))
                    {
                        continue;
                    }

                    object value = field.GetValue(graph);

                    if (object.ReferenceEquals(value, null))
                    {
                        continue;
                    }

                    Type valueType = value.GetType();

                    if (valueType.IsPrimitive || valueType == typeof(SerializationData) || valueType == typeof(string))
                    {
                        continue;
                    }

                    if (object.ReferenceEquals(value, oldReference))
                    {
                        field.SetValue(graph, newReference);
                        value = newReference;
                    }

                    if (!processedReferences.Contains(value))
                    {
                        ReplaceAllReferencesInGraph(value, oldReference, newReference, processedReferences);
                    }
                }
            }
        }