PageRenderTime 58ms CodeModel.GetById 28ms RepoModel.GetById 0ms app.codeStats 1ms

/Trunk/BReusable/Extensions/Extensions.cs

https://bitbucket.org/Maslow/breusable-codeplex
C# | 601 lines | 309 code | 63 blank | 229 comment | 48 complexity | 9f533002ba64ab68c06451d85be2bbbf MD5 | raw file
  1. using System;
  2. using System.Collections.Generic;
  3. using System.ComponentModel;
  4. using System.Globalization;
  5. using System.Linq;
  6. using System.Linq.Expressions;
  7. using System.Text;
  8. using System.Text.RegularExpressions;
  9. using BReusable;
  10. using System.Diagnostics;
  11. //TODO: make a class to divide up a path into parts
  12. /// <summary>
  13. /// These extensions should be specific enough to not clash or otherwise overfill method selection
  14. /// </summary>
  15. public static class Extensions
  16. {
  17. /// <summary>
  18. /// From
  19. /// http://davidhayden.com/blog/dave/archive/2006/11/26/IsTypeNullableTypeConverter.aspx
  20. /// </summary>
  21. /// <param name="theType"></param>
  22. /// <returns></returns>
  23. public static bool IsNullable(this Type theType)
  24. {
  25. return (theType.IsGenericType && theType.
  26. GetGenericTypeDefinition().Equals
  27. (typeof(Nullable<>)));
  28. }
  29. /// <summary>
  30. /// Alternative to using (Targ arg=new TArg()){}
  31. /// Using expression, instead of statement
  32. /// http://smellegantcode.wordpress.com/2009/02/08/a-functional-replacement-for-the-using-statement/
  33. /// </summary>
  34. /// <typeparam name="TArg"></typeparam>
  35. /// <typeparam name="TResult"></typeparam>
  36. /// <param name="arg"></param>
  37. /// <param name="usage"></param>
  38. /// <returns></returns>
  39. public static TResult Use<TArg, TResult>(
  40. this TArg arg, Func<TArg, TResult> usage)
  41. where TArg : IDisposable
  42. {
  43. try
  44. {
  45. return usage(arg);
  46. }
  47. finally
  48. {
  49. arg.Dispose();
  50. }
  51. }
  52. /// <summary>
  53. /// from: http://www.moggoly.me.uk/blog/post/Enum-description-values.aspx
  54. /// </summary>
  55. /// <typeparam name="T"></typeparam>
  56. /// <param name="value"></param>
  57. /// <returns></returns>
  58. public static string DescriptionOrToString<T>(this T value) where T:struct
  59. {
  60. var da = (DescriptionAttribute[])(typeof(T).GetField(value.ToString()).GetCustomAttributes(typeof(DescriptionAttribute), false));
  61. return da.Length > 0 ? da[0].Description : value.ToString();
  62. }
  63. public static string ToStringOrEmpty<T>(this Nullable<T> data)
  64. where T:struct
  65. {
  66. if (data.HasValue)
  67. return data.Value.ToString();
  68. return string.Empty;
  69. }
  70. /// <summary>
  71. ///
  72. /// </summary>
  73. /// <typeparam name="TResult"></typeparam>
  74. /// <param name="type"></param>
  75. /// <param name="inherit">specifies whether to search the inheritance chain for the attribute
  76. /// normally false</param>
  77. /// <returns></returns>
  78. public static IEnumerable< TResult> GetTypeAttribute<TResult>(this Type type,bool inherit) where TResult:Attribute
  79. {
  80. var attribs = (TResult[]) type.GetCustomAttributes(typeof (TResult), inherit);
  81. return attribs;
  82. }
  83. public static TResult GetTypeAttribute<TAttribute,TResult>(this Type type, bool inherit,
  84. Func<IEnumerable<TAttribute>,TResult> attributeValueFunc) where TAttribute:Attribute
  85. {
  86. return attributeValueFunc(GetTypeAttribute<TAttribute>(type, inherit));
  87. }
  88. public static TResult GetAttribute<T,TResult>(this T obj,bool inherit) where TResult:Attribute
  89. {
  90. var attribs = (TResult[]) (typeof (T).GetCustomAttributes(typeof(TResult), inherit));
  91. return attribs.Single();
  92. }
  93. public static TResult GetAttribute<T, TAttribute, TResult>(this T value, bool inherit, Func<TAttribute, TResult> attributeValueFunc)
  94. where TAttribute:Attribute
  95. {
  96. var attrib = value.GetAttribute<T,TAttribute>(inherit);
  97. return attributeValueFunc(attrib);
  98. }
  99. public static int Million(this int value)
  100. {
  101. return value * 1000000;
  102. }
  103. public static int Thousand(this int value)
  104. {
  105. return value * 1000;
  106. }
  107. /// <summary>
  108. /// Gets all combined items from an enum value.
  109. /// from: http://stackoverflow.com/questions/105372/c-how-to-enumerate-an-enum
  110. /// </summary>
  111. /// <typeparam name="T"></typeparam>
  112. /// <param name="value">The value.</param>
  113. /// <returns></returns>
  114. public static IEnumerable<T> GetAllSelectedItems<T>(this Enum value)
  115. {
  116. int valueAsInt = Convert.ToInt32(value, CultureInfo.InvariantCulture);
  117. foreach (object item in Enum.GetValues(typeof(T)))
  118. {
  119. int itemAsInt = Convert.ToInt32(item, CultureInfo.InvariantCulture);
  120. if (itemAsInt == (valueAsInt & itemAsInt))
  121. {
  122. yield return (T)item;
  123. }
  124. }
  125. }
  126. public static bool IsEven(this int i)
  127. {
  128. return i%2 == 0;
  129. }
  130. public static bool IsEven(this byte b)
  131. {
  132. return b % 2 == 0;
  133. }
  134. /// <summary>
  135. /// Usage: mytype.IsSubclassOfRawGeneric(typeof(list<>))
  136. /// From BReusable
  137. /// </summary>
  138. /// <param name="generic"></param>
  139. /// <param name="toCheck"></param>
  140. /// <returns></returns>
  141. public static bool IsSubclassOfRawGeneric(this Type toCheck, Type generic)
  142. {
  143. while (toCheck != typeof(object))
  144. {
  145. var cur = toCheck.IsGenericType ? toCheck.GetGenericTypeDefinition() : toCheck;
  146. if (generic == cur)
  147. {
  148. return true;
  149. }
  150. toCheck = toCheck.BaseType;
  151. }
  152. return false;
  153. }
  154. /// <summary>
  155. /// To suppress UI assert messages use:
  156. /// Trace.Listeners.Clear();
  157. /// </summary>
  158. /// <typeparam name="T"></typeparam>
  159. /// <param name="assertAgainst"></param>
  160. /// <param name="condition"></param>
  161. /// <param name="exception"></param>
  162. /// <returns></returns>
  163. public static T Assert<T>(this T assertAgainst, Func<T,bool> condition,Func<Exception> exception)
  164. {
  165. var conditionMet = condition(assertAgainst);
  166. if (Debugger.IsAttached)
  167. Debug.Assert(conditionMet);
  168. //assertAgainst.Assert(x => x != null, () => new NullReferenceException());
  169. if (!conditionMet)
  170. throw exception();
  171. return assertAgainst;
  172. }
  173. public static void AssertThenThrow(this bool condition)
  174. {
  175. Debug.Assert(condition);
  176. if(condition!=true)
  177. throw new Exception("Assertion failed");
  178. }
  179. public static T ThrowIfNull<T>(this T item ) where T : class
  180. {
  181. if (item == null) throw new NullReferenceException();
  182. return item;
  183. }
  184. /// <summary>
  185. /// From BReusable
  186. /// </summary>
  187. /// <param name="c"></param>
  188. /// <returns></returns>
  189. public static int ToAscii(this char c)
  190. {
  191. return c;
  192. }
  193. /// <summary>
  194. /// From BReusable
  195. /// </summary>
  196. /// <param name="text"></param>
  197. /// <returns></returns>
  198. public static IEnumerable<byte> ToAsciiList(this String text)
  199. {
  200. return Encoding.ASCII.GetBytes(text);
  201. }
  202. /// <summary>
  203. /// From BReusable
  204. /// </summary>
  205. /// <param name="text"></param>
  206. /// <param name="e"></param>
  207. /// <returns></returns>
  208. public static IEnumerable<byte> ToEncodedValues(this String text, Encoding e)
  209. {
  210. return e.GetBytes(text);
  211. }
  212. /// <summary>
  213. /// From BReusable
  214. /// </summary>
  215. /// <param name="sb"></param>
  216. /// <param name="addList"></param>
  217. /// <returns></returns>
  218. public static StringBuilder Append(this StringBuilder sb, IEnumerable<String> addList)
  219. {
  220. addList.ForEach(item => sb.Append(item));
  221. return sb;
  222. }
  223. /// <summary>
  224. /// From BReusable
  225. /// </summary>
  226. /// <param name="sb"></param>
  227. /// <param name="addList"></param>
  228. /// <returns></returns>
  229. public static StringBuilder AppendLine(this StringBuilder sb, IEnumerable<String> addList)
  230. {
  231. addList.ForEach(item => sb.AppendLine(item));
  232. return sb;
  233. }
  234. /// <summary>
  235. /// From BReusable
  236. /// </summary>
  237. /// <typeparam name="T"></typeparam>
  238. /// <param name="source"></param>
  239. /// <returns></returns>
  240. public static T DirectCast<T>(this object source)
  241. {
  242. return (T)source;
  243. }
  244. /// <summary>
  245. /// From BReusable
  246. /// </summary>
  247. /// <param name="s"></param>
  248. /// <returns></returns>
  249. public static bool IsNullOrEmpty(this String s)
  250. {
  251. return string.IsNullOrEmpty(s);
  252. }
  253. /// <summary>
  254. /// BReusable
  255. /// string.IsNullOrEmpty()==false
  256. /// </summary>
  257. /// <param name="s"></param>
  258. /// <returns></returns>
  259. public static bool HasValue(this string s)
  260. {
  261. return string.IsNullOrEmpty(s) == false;
  262. }
  263. public static bool IsIgnoreCaseMatch(this string s, string comparisonText)
  264. {
  265. return s.StrComp(comparisonText, true) == 0;
  266. }
  267. /// <summary>
  268. /// From BReusable
  269. /// </summary>
  270. /// <param name="s"></param>
  271. /// <param name="doWhatIfFalse"></param>
  272. public static void IsNullOrEmpty(this String s, Action<String> doWhatIfFalse)
  273. {
  274. if (s.IsNullOrEmpty() == false)
  275. doWhatIfFalse(s);
  276. }
  277. /// <summary>
  278. /// Checks if the string is null, empty, or just whitespace (tab, returns, spaces)
  279. /// From BReusable
  280. /// </summary>
  281. /// <param name="text"></param>
  282. /// <returns></returns>
  283. public static bool IsNullOrWhitespace(this String text)
  284. {
  285. return text.IsNullOrEmpty() || (text.IsMatch(@"^\s+$", false));
  286. }
  287. /// <summary>
  288. /// Checks if the string is null, empty, or just whitespace (tab, returns, spaces)
  289. /// From BReusable
  290. /// </summary>
  291. /// <param name="text"></param>
  292. /// <param name="doWhatIfFalse">If string is not null or whitespace, do what?</param>
  293. public static void IsNullOrWhitespace(this String text, Action<String> doWhatIfFalse)
  294. {
  295. if (text.IsNullOrWhitespace() == false) doWhatIfFalse(text);
  296. }
  297. //Not sure if this is useful
  298. //public static T IsNullOrEmpty<T>(this String s, Func<String,T> DoWhatIfFalse)
  299. //{
  300. // if (s.IsNullOrEmpty() == false)
  301. // return DoWhatIfFalse(s);
  302. // else
  303. // return default(T);
  304. //}
  305. /// <summary>
  306. /// Takes the object, does a ToString and writes it out to the debug stream
  307. /// returns the result of the ToString
  308. /// From BReusable
  309. /// </summary>
  310. /// <param name="output"></param>
  311. /// <returns></returns>
  312. public static String ToStringToDebug(this object output)
  313. {
  314. var outputString = output.ToString();
  315. Debug.WriteLine(outputString);
  316. return outputString;
  317. }
  318. /// <summary>
  319. /// From BReusable
  320. /// </summary>
  321. /// <param name="text"></param>
  322. /// <param name="doWhatIfValid"></param>
  323. public static void IsValidDateTime(this String text, Action<DateTime> doWhatIfValid)
  324. {
  325. DateTime dateTime;
  326. if (DateTime.TryParse(text, out dateTime))
  327. doWhatIfValid(dateTime);
  328. }
  329. /// <summary>
  330. /// From BReusable
  331. /// </summary>
  332. /// <param name="text"></param>
  333. /// <returns></returns>
  334. public static DateTime? IsValidDateTime(this String text)
  335. {
  336. DateTime dateTime;
  337. if (DateTime.TryParse(text, out dateTime))
  338. return dateTime;
  339. return null;
  340. }
  341. /// <summary>
  342. /// From BReusable
  343. /// </summary>
  344. /// <param name="str1"></param>
  345. /// <param name="str2"></param>
  346. /// <param name="ignoreCase"></param>
  347. /// <returns></returns>
  348. public static int StrComp(this String str1, String str2, bool ignoreCase)
  349. {
  350. return string.Compare(str1, str2, ignoreCase);
  351. }
  352. /// <summary>
  353. /// From BReusable
  354. /// </summary>
  355. /// <param name="ts"></param>
  356. /// <returns></returns>
  357. public static String WholePartOnly(this Stopwatch ts)
  358. {
  359. var time = ts.Elapsed.ToString();
  360. return Regex.Replace(time, @"\..*$", string.Empty);
  361. }
  362. /// <summary>
  363. /// From BReusable
  364. /// </summary>
  365. /// <param name="ts"></param>
  366. /// <param name="itemsProcessedDuringTimer"></param>
  367. /// <returns></returns>
  368. public static String XPerSecond(this Stopwatch ts, int itemsProcessedDuringTimer)
  369. {
  370. //var time = ts.Elapsed;
  371. return (itemsProcessedDuringTimer
  372. / (ts.ElapsedMilliseconds / 1000)).ToString();
  373. }
  374. /// <summary>
  375. /// Currently includes strings and DateTime properties
  376. /// From BReusable
  377. /// </summary>
  378. /// <typeparam name="T"></typeparam>
  379. /// <param name="o"></param>
  380. /// <returns></returns>
  381. public static IDictionary<String, Action<T, object>> MapPropertySetters<T>(this T o)
  382. {
  383. var properties = new Dictionary<string, Action<T, object>>(StringComparer.CurrentCultureIgnoreCase);
  384. System.Reflection.PropertyInfo[] s = o.GetType().GetProperties();
  385. for (int i = 0; i < s.GetUpperBound(0) + 1; i++)
  386. {
  387. var prop = s[i];
  388. if (prop.CanWrite)
  389. {
  390. if (prop.PropertyType == typeof(DateTime))
  391. {
  392. properties.Add(prop.Name, (obj, val) => prop.SetValue(obj, (DateTime)val, null));
  393. }
  394. else if (prop.PropertyType == typeof(String))
  395. properties.Add(prop.Name, (obj, val) => prop.SetValue(obj, ((String)val).Trim(), null));
  396. else if (prop.PropertyType == typeof(int))
  397. properties.Add(prop.Name, (obj, val) => prop.SetValue(obj, val, null));
  398. }
  399. }
  400. return properties;
  401. }
  402. /// <summary>
  403. /// From BReusable
  404. /// </summary>
  405. /// <param name="o"></param>
  406. /// <returns></returns>
  407. public static System.Reflection.PropertyInfo[] ReflectProperties(this object o)
  408. {
  409. return o.GetType().GetProperties();
  410. }
  411. /// <summary>
  412. /// From BReusable
  413. /// </summary>
  414. /// <param name="o"></param>
  415. /// <param name="name"></param>
  416. /// <returns></returns>
  417. public static System.Reflection.PropertyInfo ReflectProperty(this object o, String name)
  418. {
  419. return o.GetType().GetProperty(name);
  420. }
  421. /// <summary>
  422. /// From BReusable
  423. /// </summary>
  424. /// <typeparam name="T"></typeparam>
  425. /// <param name="source"></param>
  426. /// <param name="destination"></param>
  427. public static void CopyReadWriteProperties<T>(this T source, T destination)
  428. {
  429. foreach (var prop in source.ReflectProperties())
  430. {
  431. if (prop.CanRead && prop.CanWrite)
  432. {
  433. var oldValue = source.GetType().GetProperty(prop.Name).GetValue(source, null);
  434. destination.GetType().GetProperty(prop.Name).SetValue(destination, oldValue, null);
  435. }
  436. }
  437. }
  438. public static void CopyReadWriteProperties<T>(this T source, T destination, IEnumerable<string> blackList)
  439. {
  440. foreach (var property in source.ReflectProperties())
  441. {
  442. if (property.CanRead && property.CanWrite && (blackList == null || blackList.Contains(property.Name) == false))
  443. {
  444. var oldValue = source.GetType().GetProperty(property.Name).GetValue(source, null);
  445. destination.GetType().GetProperty(property.Name).SetValue(destination, oldValue, null);
  446. }
  447. }
  448. }
  449. /// <summary>
  450. /// From BReusable
  451. /// </summary>
  452. /// <param name="o"></param>
  453. /// <param name="writer"></param>
  454. public static void Dump(this object o, System.IO.TextWriter writer)
  455. {
  456. var props = o.ReflectProperties();
  457. foreach (var item in props)
  458. {
  459. try
  460. {
  461. writer.WriteLine(item.Name + ": " + item.GetValue(o, null));
  462. }
  463. catch (Exception)
  464. {
  465. writer.WriteLine(item.Name + ":" + "<unknown>");
  466. }
  467. }
  468. }
  469. /// <summary>
  470. /// From BReusable
  471. /// </summary>
  472. /// <typeparam name="T"></typeparam>
  473. /// <param name="enumString"></param>
  474. /// <returns></returns>
  475. public static T? ParseEnum<T>(this String enumString) where T : struct
  476. {
  477. if (Enum.IsDefined(typeof(T), enumString))
  478. return (T)Enum.Parse(typeof(T), enumString);
  479. return new T?();
  480. }
  481. /// <summary>
  482. /// From BReusable
  483. /// </summary>
  484. /// <param name="bytes"></param>
  485. /// <returns></returns>
  486. public static double ConvertBytesToMegabytes(this long bytes)
  487. {
  488. return (bytes / 1024f) / 1024f;
  489. }
  490. /// <summary>
  491. /// From BReusable
  492. /// </summary>
  493. /// <param name="kilobytes"></param>
  494. /// <returns></returns>
  495. public static double ConvertKilobytesToMegabytes(this long kilobytes)
  496. {
  497. return kilobytes / 1024f;
  498. }
  499. /// <summary>
  500. /// BReusable.Extensions
  501. /// </summary>
  502. /// <typeparam name="T"></typeparam>
  503. /// <param name="item"></param>
  504. /// <param name="doWhat"></param>
  505. public static void IfNotNull<T>(this T item, Action<T> doWhat) where T:class
  506. {
  507. if (item != null)
  508. doWhat(item);
  509. }
  510. /// <summary>
  511. /// BReusable.Extensions
  512. /// </summary>
  513. /// <typeparam name="T"></typeparam>
  514. /// <typeparam name="TResult"></typeparam>
  515. /// <param name="item"></param>
  516. /// <param name="doWhat"></param>
  517. /// <returns>the value or null</returns>
  518. public static TResult IfNotNull<T,TResult>(this T item, Func<T,TResult> doWhat) where T:class
  519. {
  520. if(item!=null)
  521. return doWhat(item);
  522. return default(TResult);
  523. }
  524. #region Not Actually Extensions
  525. /// <summary>
  526. /// Safe RaiseEvent to check if there is a handler or not
  527. /// From BReusable
  528. /// </summary>
  529. /// <param name="sender"></param>
  530. /// <param name="evnt"></param>
  531. public static void RaiseEvent(object sender, EventHandler evnt)
  532. {
  533. var handler = evnt;
  534. if (handler != null)
  535. handler(sender, EventArgs.Empty);
  536. }
  537. #endregion
  538. }