PageRenderTime 43ms CodeModel.GetById 26ms RepoModel.GetById 0ms app.codeStats 0ms

/Utilities/Collections/EnumerableExtensions.cs

#
C# | 151 lines | 95 code | 10 blank | 46 comment | 0 complexity | f16739cab01468794a14c215d52cca9b MD5 | raw file
Possible License(s): Apache-2.0
  1. using System;
  2. using System.Collections.Generic;
  3. using NUnit.Framework;
  4. namespace Delta.Utilities.Collections
  5. {
  6. /// <summary>
  7. /// Extensions to <see cref="IEnumerable{T}"/>, make sure to use this
  8. /// namespace when using this extensions. Includes ForEach, TryDo, Do and
  9. /// EnumerateAll methods for IEnumerable items.
  10. /// </summary>
  11. public static class EnumerableExtensions
  12. {
  13. #region ForEach (Static)
  14. /// <summary>
  15. /// Iterates the <paramref name="source"/> and applies the
  16. /// <paramref name="action"/> to each item.
  17. /// </summary>
  18. /// <typeparam name="TItem">TItem</typeparam>
  19. /// <param name="action">Action</param>
  20. /// <param name="source">Source</param>
  21. public static void ForEach<TItem>(this IEnumerable<TItem> source,
  22. Action<TItem> action)
  23. {
  24. foreach (var item in source)
  25. {
  26. action(item);
  27. }
  28. }
  29. #endregion
  30. #region TryDo (Static)
  31. /// <summary>
  32. /// Allows chaining actions on a set of items for later processing,
  33. /// filtering or projection (transformation), ignoring exceptions that
  34. /// might happen in the action.
  35. /// </summary>
  36. /// <typeparam name="T">T</typeparam>
  37. /// <param name="action">Action</param>
  38. /// <param name="source">Source</param>
  39. /// <returns>An enumeration with the same items as the source.</returns>
  40. public static IEnumerable<T> TryDo<T>(this IEnumerable<T> source,
  41. Action<T> action)
  42. {
  43. foreach (var item in source)
  44. {
  45. try
  46. {
  47. action(item);
  48. }
  49. catch
  50. {
  51. }
  52. yield return item;
  53. }
  54. }
  55. #endregion
  56. #region Do (Static)
  57. /// <summary>
  58. /// Allows chaining actions on a set of items for later processing,
  59. /// filtering or projection (transformation).
  60. /// </summary>
  61. /// <typeparam name="T">T</typeparam>
  62. /// <param name="action">Action</param>
  63. /// <param name="source">Source</param>
  64. /// <returns>An enumeration with the same items as the source.</returns>
  65. public static IEnumerable<T> Do<T>(this IEnumerable<T> source,
  66. Action<T> action)
  67. {
  68. foreach (var item in source)
  69. {
  70. action(item);
  71. yield return item;
  72. }
  73. }
  74. #endregion
  75. #region EnumerateAll (Static)
  76. /// <summary>
  77. /// Enumerates all elements in the source, so that any intermediate
  78. /// action or side-effect from it is performed eagerly.
  79. /// Note: Does nothing inside the enumeration!
  80. /// </summary>
  81. /// <typeparam name="T">T</typeparam>
  82. /// <param name="source">Source</param>
  83. public static void EnumerateAll<T>(this IEnumerable<T> source)
  84. {
  85. foreach (var item in source)
  86. {
  87. }
  88. }
  89. #endregion
  90. /// <summary>
  91. /// Tests for EnumerableExtensions. Not really useful, we just use some
  92. /// numbers to test the functionality, but in order to use this class for
  93. /// real a state machine (e.g. for AI) should be used.
  94. /// </summary>
  95. internal class EnumerableExtensionsTests
  96. {
  97. #region TestForEach
  98. [Test]
  99. public void TestForEach()
  100. {
  101. List<int> someNumbers = new List<int>();
  102. someNumbers.Add(1);
  103. someNumbers.Add(2);
  104. someNumbers.Add(5);
  105. someNumbers.Add(10);
  106. // And add all numbers
  107. int allNumbers = 0;
  108. someNumbers.ForEach(delegate(int number)
  109. {
  110. allNumbers += number;
  111. });
  112. Assert.Equal(allNumbers, 1 + 2 + 5 + 10);
  113. }
  114. #endregion
  115. #region TestDo
  116. [Test, Category("LongRunning")]
  117. public void TestDo()
  118. {
  119. List<int> someNumbers = new List<int>();
  120. someNumbers.Add(1);
  121. someNumbers.Add(2);
  122. someNumbers.Add(5);
  123. someNumbers.Add(10);
  124. // Define action what to do when calling the Do method below
  125. Action<int> printNumberAndSquare = delegate(int number)
  126. {
  127. Console.WriteLine(
  128. "Number: " + number + ", Square: " + number * number);
  129. };
  130. // And print them all out, calling them one by one
  131. // Note: This is obviously not very useful code, it just shows how
  132. // to use the Do method. You need more useful state machine code!
  133. foreach (int number in someNumbers.Do(printNumberAndSquare))
  134. {
  135. Console.WriteLine("Processed number: " + number);
  136. }
  137. }
  138. #endregion
  139. }
  140. }
  141. }