public GraphRef( GraphRef parent, object obj, string propName) { this.parent = parent; this.value = obj; this.propName = propName; }
public GraphRef( GraphRef parent, object obj, string propName) { Parent = parent; Value = obj; PropName = propName; }
private static void reflect( StringBuilder sb, GraphRef obj, int indent, bool deep, int nestingLevel = 0) { const int maxDepth = 3; //Ensure that we are not following a circular reference path if (!(obj.Value is ValueType)) { var parentRef = obj.Parent; while (parentRef != null) { if (parentRef.Value == obj.Value) { return; } parentRef = parentRef.Parent; } } sb.Append('\t', indent); //Output property name if applicable if (!string.IsNullOrEmpty(obj.PropName)) { sb.Append(obj.PropName); sb.Append(@"="); } var childIndent = indent + 1; //If value is null, output "null" if (obj.Value == null) { sb.Append(@"null"); } //If value is a string, output value with quotes around it else { if (obj.Value is string s) { sb.AppendFormat(@"""{0}""", escape(s)); } //If value is a char, output value with single quotes around it else if (obj.Value is char) { sb.AppendFormat(@"'{0}'", escape(new string((char)obj.Value, 1))); } else { if (obj.Value is IDictionary value) { var list = value; sb.Append(Environment.NewLine); sb.Append('\t', indent); sb.Append(@"["); sb.Append(Environment.NewLine); foreach (DictionaryEntry entry in list) { reflect(sb, new GraphRef(obj, entry.Key, null), childIndent, deep, nestingLevel); sb.Append(@" = "); reflect(sb, new GraphRef(obj, entry.Value, null), childIndent, deep, nestingLevel); sb.Append(Environment.NewLine); } sb.Append('\t', indent); sb.Append(@"]"); sb.Append(Environment.NewLine); } //If it's a Type object, we don't want to endlessly follow long trains of //interconnected type info objects else { var type1 = obj.Value as Type; if (type1 != null) { sb.Append(@"Type: "); sb.Append(type1.FullName); } //...and similarly for MemberInfo objects else { var info = obj.Value as MemberInfo; if (info != null) { sb.Append(info.GetType().Name); sb.Append(@": "); sb.Append(info.Name); } //If value is not of a basic datatype else if (Convert.GetTypeCode(obj.Value) == TypeCode.Object) { var type = obj.Value.GetType(); sb.Append(type.Name); //might want to use type.FullName instead. if (indent <= maxDepth && (deep || nestingLevel == 0)) { sb.Append(Environment.NewLine); sb.Append('\t', indent); sb.Append(@"{"); sb.Append(Environment.NewLine); //Get all the properties in the object's type var props = type.GetProperties( BindingFlags.Public | BindingFlags.Instance | BindingFlags.FlattenHierarchy); //Enumerate all the properties and output their values for (var i = 0; i < props.Length; i++) { var pi = props[i]; if (pi.GetIndexParameters().Length == 0) //Ignore indexers { try { reflect(sb, new GraphRef(obj, pi.GetValue(obj.Value, null), pi.Name), childIndent, deep, nestingLevel + 1); } catch (Exception e) { sb.Append(@"<Error getting property value ("); sb.Append(e.GetType().Name); sb.Append(@")>"); } if (i < props.Length - 1) { sb.Append(','); } sb.Append(Environment.NewLine); } } //If IList, output all the values in the list if (obj.Value is IList list) { sb.Append(Environment.NewLine); for (var i = 0; i < list.Count; i++) { reflect(sb, new GraphRef(obj, list[i], null), childIndent, deep, nestingLevel + 1); if (i < list.Count - 1) { sb.Append(','); } sb.Append(Environment.NewLine); } } sb.Append('\t', indent); sb.Append(@"}"); } } //If value is of a basic datatype else { sb.Append(obj.Value); } } } } } }
/// <summary> /// Initializes a new instance of the <see cref="GraphRef"/> class. /// </summary> /// <param name="parent">The parent.</param> /// <param name="obj">The obj.</param> /// <param name="propName">Name of the prop.</param> public GraphRef(GraphRef parent, object obj, string propName) { _parent = parent; _value = obj; _propName = propName; }
/// <summary> /// Reflects the specified sb. /// </summary> /// <param name="sb">The sb.</param> /// <param name="obj">The obj.</param> /// <param name="indent">The indent.</param> /// <param name="flags">The flags.</param> /// <param name="maxDepth">The max depth.</param> private static void Reflect(StringBuilder sb, GraphRef obj, int indent, BindingFlags flags, int maxDepth) { //Ensure that we are not following a circular reference path if ((obj.Value is ValueType) == false) { GraphRef parentRef = obj.Parent; while (parentRef != null) { if (parentRef.Value == obj.Value) return; parentRef = parentRef.Parent; } } sb.Append('\t', indent); //Output property name if applicable if (!String.IsNullOrEmpty(obj.PropName)) { sb.Append(obj.PropName); sb.Append("="); } int childIndent = indent + 1; //If value is null, output "null" if (obj.Value == null) { sb.Append("null"); } //If value is a string, output value with quotes around it else if (obj.Value is string) { sb.Append("\"" + Escape((string)obj.Value) + "\""); } //If value is a char, output value with single quotes around it else if (obj.Value is char) { sb.Append("\'" + Escape(new String((char)obj.Value, 1)) + "\'"); } //If value is a XmlNode, output xml value with quotes around it else if (obj.Value is System.Xml.XmlNode) { sb.AppendLine("\""); sb.AppendLine(((System.Xml.XmlNode)obj.Value).OuterXml); sb.AppendLine("\""); } //If value is an IEnumerable, output all the items else if (obj.Value is IEnumerable) { sb.AppendLine(); sb.Append('\t', indent); sb.Append("["); sb.AppendLine(); IEnumerator enumerator = ((IEnumerable)obj.Value).GetEnumerator(); while (enumerator.MoveNext()) { Reflect(sb, new GraphRef(obj, enumerator.Current, null), childIndent, flags, maxDepth); sb.AppendLine(","); } sb.Append('\t', indent); sb.Append("]"); } //If it's a Type object, we don't want to endlessly follow long trains of //interconnected type info objects else if (obj.Value is Type) { sb.Append("Type: "); sb.Append(((Type)obj.Value).FullName); } //...and similarly for MemberInfo objects else if (obj.Value is MemberInfo) { sb.Append(obj.Value.GetType().Name); sb.Append(": "); sb.Append(((MemberInfo)obj.Value).Name); } //If value is not of a basic datatype else if (Convert.GetTypeCode(obj.Value) == TypeCode.Object) { Type type = obj.Value.GetType(); sb.Append(type.Name); //might want to use type.FullName instead if (indent <= maxDepth) { sb.AppendLine(); sb.Append('\t', indent); sb.AppendLine("{"); //Get all the fileds in the object's type FieldInfo[] fields = type.GetFields(flags); //Enumerate all the properties and output their values for (int i = 0; i < fields.Length; i++) { FieldInfo fi = fields[i]; try { Reflect(sb, new GraphRef(obj, fi.GetValue(obj.Value), fi.Name), childIndent, flags, maxDepth); } catch (Exception e) { sb.Append("<Error getting field value (" + e.GetType().Name + ") " + fi.Name + ">"); } if (i < fields.Length - 1) sb.Append(','); sb.AppendLine(); } //Get all the properties in the object's type PropertyInfo[] props = type.GetProperties(flags); //Enumerate all the properties and output their values for (int i = 0; i < props.Length; i++) { PropertyInfo pi = props[i]; if (pi.GetIndexParameters().Length == 0) //Ignore indexers { try { Reflect(sb, new GraphRef(obj, pi.GetValue(obj.Value, null), pi.Name), childIndent, flags, maxDepth); } catch (Exception e) { sb.Append("<Error getting property value (" + e.GetType().Name + ") " + pi.Name + ">"); } if (i < props.Length - 1) sb.Append(','); sb.AppendLine(); } } sb.Append('\t', indent); sb.Append("}"); } } //If value is of a basic datatype else { sb.Append(obj.Value.ToString()); } }
/// <summary> /// Reflects the specified sb. /// </summary> /// <param name="sb">The sb.</param> /// <param name="obj">The obj.</param> /// <param name="indent">The indent.</param> /// <param name="flags">The flags.</param> /// <param name="maxDepth">The max depth.</param> private static void Reflect(StringBuilder sb, GraphRef obj, int indent, BindingFlags flags, int maxDepth) { //Ensure that we are not following a circular reference path if ((obj.Value is ValueType) == false) { GraphRef parentRef = obj.Parent; while (parentRef != null) { if (parentRef.Value == obj.Value) { return; } parentRef = parentRef.Parent; } } sb.Append('\t', indent); //Output property name if applicable if (!String.IsNullOrEmpty(obj.PropName)) { sb.Append(obj.PropName); sb.Append("="); } int childIndent = indent + 1; //If value is null, output "null" if (obj.Value == null) { sb.Append("null"); } //If value is a string, output value with quotes around it else if (obj.Value is string) { sb.Append("\"" + Escape((string)obj.Value) + "\""); } //If value is a char, output value with single quotes around it else if (obj.Value is char) { sb.Append("\'" + Escape(new String((char)obj.Value, 1)) + "\'"); } //If value is a XmlNode, output xml value with quotes around it else if (obj.Value is System.Xml.XmlNode) { sb.AppendLine("\""); sb.AppendLine(((System.Xml.XmlNode)obj.Value).OuterXml); sb.AppendLine("\""); } //If value is an IEnumerable, output all the items else if (obj.Value is IEnumerable) { sb.AppendLine(); sb.Append('\t', indent); sb.Append("["); sb.AppendLine(); IEnumerator enumerator = ((IEnumerable)obj.Value).GetEnumerator(); while (enumerator.MoveNext()) { Reflect(sb, new GraphRef(obj, enumerator.Current, null), childIndent, flags, maxDepth); sb.AppendLine(","); } sb.Append('\t', indent); sb.Append("]"); } //If it's a Type object, we don't want to endlessly follow long trains of //interconnected type info objects else if (obj.Value is Type) { sb.Append("Type: "); sb.Append(((Type)obj.Value).FullName); } //...and similarly for MemberInfo objects else if (obj.Value is MemberInfo) { sb.Append(obj.Value.GetType().Name); sb.Append(": "); sb.Append(((MemberInfo)obj.Value).Name); } //If value is not of a basic datatype else if (Convert.GetTypeCode(obj.Value) == TypeCode.Object) { Type type = obj.Value.GetType(); sb.Append(type.Name); //might want to use type.FullName instead if (indent <= maxDepth) { sb.AppendLine(); sb.Append('\t', indent); sb.AppendLine("{"); //Get all the fileds in the object's type FieldInfo[] fields = type.GetFields(flags); //Enumerate all the properties and output their values for (int i = 0; i < fields.Length; i++) { FieldInfo fi = fields[i]; try { Reflect(sb, new GraphRef(obj, fi.GetValue(obj.Value), fi.Name), childIndent, flags, maxDepth); } catch (Exception e) { sb.Append("<Error getting field value (" + e.GetType().Name + ") " + fi.Name + ">"); } if (i < fields.Length - 1) { sb.Append(','); } sb.AppendLine(); } //Get all the properties in the object's type PropertyInfo[] props = type.GetProperties(flags); //Enumerate all the properties and output their values for (int i = 0; i < props.Length; i++) { PropertyInfo pi = props[i]; if (pi.GetIndexParameters().Length == 0) //Ignore indexers { try { Reflect(sb, new GraphRef(obj, pi.GetValue(obj.Value, null), pi.Name), childIndent, flags, maxDepth); } catch (Exception e) { sb.Append("<Error getting property value (" + e.GetType().Name + ") " + pi.Name + ">"); } if (i < props.Length - 1) { sb.Append(','); } sb.AppendLine(); } } sb.Append('\t', indent); sb.Append("}"); } } //If value is of a basic datatype else { sb.Append(obj.Value.ToString()); } }
private static void Reflect( StringBuilder sb, GraphRef obj, int indent) { const int maxDepth = 3; if (!(obj.Value is ValueType)) { GraphRef parentRef = obj.Parent; while (parentRef != null) { if (parentRef.Value == obj.Value) { return; } parentRef = parentRef.Parent; } } sb.Append('\t', indent); if (!String.IsNullOrEmpty(obj.PropName)) { sb.Append(obj.PropName); sb.Append("="); } int childIndent = indent + 1; if (obj.Value == null) { sb.Append("null"); } else if (obj.Value is string) { sb.Append("\"" + Escape((string)obj.Value) + "\""); } else if (obj.Value is char) { sb.Append("\'" + Escape(new String((char)obj.Value, 1)) + "\'"); } else if (obj.Value is Array) { Array arr = (Array)obj.Value; sb.Append("\r\n"); sb.Append('\t', indent); sb.Append("[\r\n"); for (int i = 0; i < arr.Length; i++) { Reflect(sb, new GraphRef(obj, arr.GetValue(i), null), childIndent); if (i < arr.Length - 1) { sb.Append(','); } sb.Append("\r\n"); } sb.Append('\t', indent); sb.Append("]\r\n"); } else if (obj.Value is Type) { sb.Append("Type: "); sb.Append(((Type)obj.Value).FullName); } else if (obj.Value is MemberInfo) { sb.Append(obj.Value.GetType().Name); sb.Append(": "); sb.Append(((MemberInfo)obj.Value).Name); } else if (Convert.GetTypeCode(obj.Value) == TypeCode.Object) { Type type = obj.Value.GetType(); sb.Append(type.Name); if (indent <= maxDepth) { sb.Append("\r\n"); sb.Append('\t', indent); sb.Append("{\r\n"); FieldInfo[] fields = type.GetFields(BindingFlags.Public | BindingFlags.Instance | BindingFlags.FlattenHierarchy); for (int i = 0; i < fields.Length; i++) { FieldInfo pi = fields[i]; try { Reflect(sb, new GraphRef(obj, pi.GetValue(obj.Value), pi.Name), childIndent); } catch (Exception e) { sb.Append("<失败获取属性值 ("); sb.Append(e.GetType().Name); sb.Append(")>"); } if (i < fields.Length - 1) { sb.Append(','); } sb.Append("\r\n"); } PropertyInfo[] props = type.GetProperties(BindingFlags.Public | BindingFlags.Instance | BindingFlags.FlattenHierarchy); for (int i = 0; i < props.Length; i++) { PropertyInfo pi = props[i]; if (pi.GetIndexParameters().Length == 0) { try { Reflect(sb, new GraphRef(obj, pi.GetValue(obj.Value, null), pi.Name), childIndent); } catch (Exception e) { sb.Append("<失败获取属性值 ("); sb.Append(e.GetType().Name); sb.Append(")>"); } if (i < props.Length - 1) { sb.Append(','); } sb.Append("\r\n"); } } if (obj is IList) { IList list = (IList)obj.Value; sb.Append("\r\n"); sb.Append('\t', indent); sb.Append("[\r\n"); for (int i = 0; i < list.Count; i++) { Reflect(sb, new GraphRef(obj, list[i], null), childIndent); if (i < list.Count - 1) { sb.Append(','); } sb.Append("\r\n"); } sb.Append('\t', indent); sb.Append("]\r\n"); } sb.Append('\t', indent); sb.Append("}"); } } else { sb.Append(obj.Value.ToString()); } }
/// <summary> /// Initializes a new instance of the <see cref="GraphRef"/> class. /// </summary> /// <param name="parent">The parent.</param> /// <param name="obj">The obj.</param> /// <param name="propName">Name of the prop.</param> public GraphRef( GraphRef parent, object obj, string propName ) { this.parent = parent; this.value = obj; this.propName = propName; }
/// <summary> /// Reflects the specified sb. /// </summary> /// <param name="sb">The sb.</param> /// <param name="obj">The obj.</param> /// <param name="indent">The indent.</param> private static void Reflect( StringBuilder sb, GraphRef obj, int indent ) { const int maxDepth = 3; //Ensure that we are not following a circular reference path if ( !(obj.Value is ValueType) ) { GraphRef parentRef = obj.Parent; while ( parentRef != null ) { if ( parentRef.Value == obj.Value ) return; parentRef = parentRef.Parent; } } sb.Append( '\t', indent ); //Output property name if applicable if ( !String.IsNullOrEmpty( obj.PropName ) ) { sb.Append( obj.PropName ); sb.Append( "=" ); } int childIndent = indent + 1; //If value is null, output "null" if ( obj.Value == null ) { sb.Append( "null" ); } //If value is a string, output value with quotes around it else if ( obj.Value is string ) { sb.Append( "\"" + Escape( (string)obj.Value ) + "\"" ); } //If value is a char, output value with single quotes around it else if ( obj.Value is char ) { sb.Append( "\'" + Escape( new String( (char)obj.Value, 1 ) ) + "\'" ); } //If value is an array, output each array element else if ( obj.Value is Array ) { Array arr = (Array)obj.Value; sb.Append( "\r\n" ); sb.Append( '\t', indent ); sb.Append( "[\r\n" ); for ( int i = 0; i < arr.Length; i++ ) { Reflect( sb, new GraphRef( obj, arr.GetValue( i ), null ), childIndent ); if ( i < arr.Length - 1 ) sb.Append( ',' ); sb.Append( "\r\n" ); } sb.Append( '\t', indent ); sb.Append( "]\r\n" ); } //If it's a Type object, we don't want to endlessly follow long trains of //interconnected type info objects else if ( obj.Value is Type ) { sb.Append( "Type: " ); sb.Append( ((Type)obj.Value).FullName ); } //...and similarly for MemberInfo objects else if ( obj.Value is MemberInfo ) { sb.Append( obj.Value.GetType().Name ); sb.Append( ": " ); sb.Append( ((MemberInfo)obj.Value).Name ); } //If value is not of a basic datatype else if ( Convert.GetTypeCode( obj.Value ) == TypeCode.Object ) { Type type = obj.Value.GetType(); sb.Append( type.Name ); //might want to use type.FullName instead if ( indent <= maxDepth ) { sb.Append( "\r\n" ); sb.Append( '\t', indent ); sb.Append( "{\r\n" ); //Get all the properties in the object's type PropertyInfo[] props = type.GetProperties( BindingFlags.Public | BindingFlags.Instance | BindingFlags.FlattenHierarchy ); //Enumerate all the properties and output their values for ( int i = 0; i < props.Length; i++ ) { PropertyInfo pi = props[i]; if ( pi.GetIndexParameters().Length == 0 ) //Ignore indexers { try { Reflect( sb, new GraphRef( obj, pi.GetValue( obj.Value, null ), pi.Name ), childIndent ); } catch ( Exception e ) { sb.Append( "<Error getting property value (" ); sb.Append( e.GetType().Name ); sb.Append( ")>" ); } if ( i < props.Length - 1 ) sb.Append( ',' ); sb.Append( "\r\n" ); } } //If IList, output all the values in the list if ( obj is IList ) { IList list = (IList)obj.Value; sb.Append( "\r\n" ); sb.Append( '\t', indent ); sb.Append( "[\r\n" ); for ( int i = 0; i < list.Count; i++ ) { Reflect( sb, new GraphRef( obj, list[i], null ), childIndent ); if ( i < list.Count - 1 ) sb.Append( ',' ); sb.Append( "\r\n" ); } sb.Append( '\t', indent ); sb.Append( "]\r\n" ); } sb.Append( '\t', indent ); sb.Append( "}" ); } } //If value is of a basic datatype else { sb.Append( obj.Value.ToString() ); } }