/src/NUnit/core/TypeHelper.cs
C# | 209 lines | 165 code | 38 blank | 6 comment | 99 complexity | f74510fdcbb360355e070464b58658aa MD5 | raw file
1// **************************************************************** 2// Copyright 2008, Charlie Poole 3// This is free software licensed under the NUnit license. You may 4// obtain a copy of the license at http://nunit.org. 5// **************************************************************** 6 7using System; 8using System.Reflection; 9using System.Text; 10using System.Text.RegularExpressions; 11 12namespace NUnit.Core 13{ 14 public class TypeHelper 15 { 16 public static string GetDisplayName(Type type) 17 { 18#if NET_2_0 19 if (type.IsGenericParameter) 20 return type.Name; 21 22 if (type.IsGenericType) 23 { 24 string name = type.FullName; 25 26 int index = name.IndexOf("[["); 27 if (index > 0) 28 { 29 int index2 = name.LastIndexOf("]]"); 30 if (index2 > index) 31 name = name.Substring(0, index) + name.Substring(index2 + 2); 32 } 33 34 index = name.LastIndexOf('.'); 35 if (index >= 0) name = name.Substring(index + 1); 36 37 index = name.IndexOf('`'); 38 while (index >= 0) 39 { 40 int index2 = name.IndexOf('+', index); 41 if (index2 >= 0) 42 name = name.Substring(0, index) + name.Substring(index2); 43 else 44 name = name.Substring(0, index); 45 46 index = name.IndexOf('`'); 47 } 48 49 StringBuilder sb = new StringBuilder(name); 50 51 sb.Append("<"); 52 int cnt = 0; 53 foreach (Type t in type.GetGenericArguments()) 54 { 55 if (cnt++ > 0) sb.Append(","); 56 sb.Append(GetDisplayName(t)); 57 } 58 sb.Append(">"); 59 60 return sb.ToString(); 61 } 62#endif 63 int lastdot = type.FullName.LastIndexOf('.'); 64 return lastdot >= 0 65 ? type.FullName.Substring(lastdot + 1) 66 : type.FullName; 67 } 68 69 public static string GetDisplayName(Type type, object[] arglist) 70 { 71 string baseName = GetDisplayName(type); 72 if (arglist == null || arglist.Length == 0) 73 return baseName; 74 75 StringBuilder sb = new StringBuilder( baseName ); 76 77 sb.Append("("); 78 for (int i = 0; i < arglist.Length; i++) 79 { 80 if (i > 0) sb.Append(","); 81 82 object arg = arglist[i]; 83 string display = arg == null ? "null" : arg.ToString(); 84 85 if (arg is double || arg is float) 86 { 87 if (display.IndexOf('.') == -1) 88 display += ".0"; 89 display += arg is double ? "d" : "f"; 90 } 91 else if (arg is decimal) display += "m"; 92 else if (arg is long) display += "L"; 93 else if (arg is ulong) display += "UL"; 94 else if (arg is string) display = "\"" + display + "\""; 95 96 sb.Append(display); 97 } 98 sb.Append(")"); 99 100 return sb.ToString(); 101 } 102 103 public static Type BestCommonType(Type type1, Type type2) 104 { 105 if (type1 == type2) return type1; 106 if (type1 == null) return type2; 107 if (type2 == null) return type1; 108 109 if (TypeHelper.IsNumeric(type1) && TypeHelper.IsNumeric(type2)) 110 { 111 if (type1 == typeof(double)) return type1; 112 if (type2 == typeof(double)) return type2; 113 114 if (type1 == typeof(float)) return type1; 115 if (type2 == typeof(float)) return type2; 116 117 if (type1 == typeof(decimal)) return type1; 118 if (type2 == typeof(decimal)) return type2; 119 120 if (type1 == typeof(UInt64)) return type1; 121 if (type2 == typeof(UInt64)) return type2; 122 123 if (type1 == typeof(Int64)) return type1; 124 if (type2 == typeof(Int64)) return type2; 125 126 if (type1 == typeof(UInt32)) return type1; 127 if (type2 == typeof(UInt32)) return type2; 128 129 if (type1 == typeof(Int32)) return type1; 130 if (type2 == typeof(Int32)) return type2; 131 132 if (type1 == typeof(UInt16)) return type1; 133 if (type2 == typeof(UInt16)) return type2; 134 135 if (type1 == typeof(Int16)) return type1; 136 if (type2 == typeof(Int16)) return type2; 137 138 if (type1 == typeof(byte)) return type1; 139 if (type2 == typeof(byte)) return type2; 140 141 if (type1 == typeof(sbyte)) return type1; 142 if (type2 == typeof(sbyte)) return type2; 143 } 144 145 return type1; 146 } 147 148 public static bool IsNumeric(Type type) 149 { 150 return type == typeof(double) || 151 type == typeof(float) || 152 type == typeof(decimal) || 153 type == typeof(Int64) || 154 type == typeof(Int32) || 155 type == typeof(Int16) || 156 type == typeof(UInt64) || 157 type == typeof(UInt32) || 158 type == typeof(UInt16) || 159 type == typeof(byte) || 160 type == typeof(sbyte); 161 } 162 163#if NET_2_0 164 public static Type MakeGenericType(Type type, Type[] typeArgs) 165 { 166 // TODO: Add error handling 167 return type.MakeGenericType(typeArgs); 168 } 169 170 public static bool CanDeduceTypeArgsFromArgs(Type type, object[] arglist, ref Type[] typeArgsOut) 171 { 172 Type[] typeParameters = type.GetGenericArguments(); 173 174 foreach (ConstructorInfo ctor in type.GetConstructors()) 175 { 176 ParameterInfo[] parameters = ctor.GetParameters(); 177 if (parameters.Length != arglist.Length) 178 continue; 179 180 Type[] typeArgs = new Type[typeParameters.Length]; 181 for (int i = 0; i < typeArgs.Length; i++) 182 { 183 for (int j = 0; j < arglist.Length; j++) 184 { 185 if (parameters[j].ParameterType.Equals(typeParameters[i])) 186 typeArgs[i] = TypeHelper.BestCommonType( 187 typeArgs[i], 188 arglist[j].GetType()); 189 } 190 191 if (typeArgs[i] == null) 192 { 193 typeArgs = null; 194 break; 195 } 196 } 197 198 if (typeArgs != null) 199 { 200 typeArgsOut = typeArgs; 201 return true; 202 } 203 } 204 205 return false; 206 } 207#endif 208 } 209}