/branches/adinetz03/runtime/CBucks.Common/ArrOps.cs
C# | 1382 lines | 710 code | 73 blank | 599 comment | 276 complexity | 038b134747acd51fdab07e68a898f6d0 MD5 | raw file
Possible License(s): AGPL-3.0
Large files files are truncated, but you can click here to view the full file
- using System;
- using System.Collections.Generic;
- using System.Text;
- using Wintellect.PowerCollections;
- using System.Diagnostics;
-
- namespace CBucks.Common {
-
- public delegate bool DoublePred<T1, T2>(T1 a, T2 b);
-
- public delegate T3 Transform<T1, T2, T3>(T1 a, T2 b);
-
- /// <summary>
- /// Contains common array operations
- /// </summary>
- public static class ArrOps {
-
- /// <summary>
- /// Gets whether any element of the array is equal to the
- /// specified value
- /// </summary>
- /// <typeparam name="T"> The value of the element </typeparam>
- /// <param name="a"> The array to check </param>
- /// <param name="val"> The value to compare with </param>
- /// <returns> True if it contains the value and false if not </returns>
- public static bool contains<T>(T[] a, T val) {
- if(null == a)
- return false;
- for(int i = 0; i < a.Length; i++) {
- if(object.Equals(a[i], val))
- return true;
- } // end of for()
- return false;
- } // end of contains<T>()
-
- /// <summary>
- /// Gets the last element of the array.
- /// </summary>
- /// <typeparam name="T"> The type of the array element </typeparam>
- /// <param name="a"> The array from which to get the last element </param>
- /// <returns> The last element of the array </returns>
- /// <exception cref="System.IndexOutOfRangeException"> The array length
- /// is zero </exception>
- /// <exception cref="System.NullReferenceException"> The <paramref name="a"/>
- /// is null </exception>
- public static T last<T>(T[] a) {
- return a[a.Length - 1];
- } // end of last()
-
- /// <summary>
- /// Removes all null entries from the array.
- /// </summary>
- /// <typeparam name="T"> The array type. </typeparam>
- /// <param name="a"> The array to remove nulls from. </param>
- /// <returns> The resulting array. </returns>
- public static T[] removeNulls<T>(T[] a) where T : class {
- List<T> l = new List<T>();
- for(int i = 0; i < a.Length; i++)
- if(null != a[i])
- l.Add(a[i]);
- return l.ToArray();
- } // end of removeNulls<T>()
-
- /// <summary>
- /// Performs a stable in-place sort of the specified array using one of
- /// stable sort algorithms
- /// </summary>
- /// <typeparam name="T"> The type of the array element </typeparam>
- /// <param name="a"> The array to be sorted in-place </param>
- /// <param name="c"> The comparison delegate </param>
- public static void stableSort<T>(T[] a, Comparison<T> c) {
- bubbleSort(a, c);
- } // end of stableSort()
-
- /// <summary>
- /// Performs in-place bubble sort of the specified array
- /// </summary>
- /// <typeparam name="T"> The type of the array element </typeparam>
- /// <param name="a"> The array to sort </param>
- /// <param name="c"> The comparison delegate </param>
- public static void bubbleSort<T>(T[] a, Comparison<T> c) {
- int n = a.Length;
- for(int i = 0; i < n; i++) {
- for(int j = i - 1; j > -1; j--)
- if(c(a[j], a[j + 1]) > 0) {
- T t = a[j];
- a[j] = a[j + 1];
- a[j + 1] = t;
- } // end of if()
- } // end of for()
- } // end of bubbleSort()
-
- /// <summary>
- /// Checks whether the <paramref name="a"/> ordered array includes
- /// the <paramref name="b"/> ordered array, i.e., contains at least
- /// all elements contained in <paramref name="b"/>
- /// </summary>
- /// <typeparam name="T"> The type of the array to check for
- /// inclusion </typeparam>
- /// <param name="a"> The first array </param>
- /// <param name="b"> The second array </param>
- /// <returns> True if the first array fully includes the second and
- /// false otherwise </returns>
- public static bool ordIncludes<T>(T[] a, T[] b) where T
- : IComparable<T> {
- if(null == b || b.Length == 0)
- return true;
- if(null == a || a.Length == 0)
- return false;
- if(a.Length < b.Length)
- return false;
- int ia = 0, ib = 0;
- while(true) {
- if(ib == b.Length)
- return true;
- if(ia == a.Length)
- return false;
- T aa = a[ia], bb = b[ib];
- int r = aa.CompareTo(bb);
- if(r < 0)
- ia++;
- else if(r == 0) {
- ia++; ib++;
- } else
- return false;
- } // end of while()
- } // end of ordIncludes<T>()
-
- /// <summary>
- /// Checks whether the array contains a null value
- /// </summary>
- /// <typeparam name="T"> The type of the array </typeparam>
- /// <param name="a"> The array to check </param>
- /// <returns> True if the array contains a null value and
- /// false if not </returns>
- public static bool hasNull<T>(T[] a) where T : class {
- if(null == a)
- return false;
- return contains<T>(a, null);
- } // end of hasNull<T>()
-
- /// <summary>
- /// Gets the sum of the elements of the array
- /// </summary>
- /// <param name="a"> The array whose elements to sum </param>
- /// <returns> The sum of the array elements </returns>
- public static double sum(double[] a) {
- double r = 0;
- for(int i = 0; i < a.Length; i++)
- r += a[i];
- return r;
- } // end of sum()
-
- /// <summary>
- /// Creates a value mask for the array
- /// </summary>
- /// <typeparam name="T"> The type of the array </typeparam>
- /// <param name="a"> The array for which to create a value
- /// mask </param>
- /// <param name="val"> The value </param>
- /// <returns> The mask which contains 0's in the position
- /// where the element of <paramref name="a"/> equals to the
- /// <paramref name="val"/> and 1's in all other positions.
- /// If the length of the array is less than sizeof(int) * 8, then
- /// remaining positions are set to 0 </returns>
- public static int valueMask<T>(T[] a, T val) {
- int i = 0;
- int n = Math.Min(32, a.Length);
- for(int j = 0; j < n; j++)
- if(!object.Equals(a[j], val))
- i |= 1 << j;
- return i;
- } // end of valueMask<T>()
-
- /// <summary>
- /// Checks whether the specified arrays are equal, i.e., contain equal
- /// components and are of same length.
- /// </summary>
- /// <typeparam name="T"> The first array </typeparam>
- /// <param name="a"> The first array </param>
- /// <param name="b"> The second array </param>
- /// <returns> True if they are equal and false if not </returns>
- public static bool equal<T>(T[] a, T[] b) {
- if(null == a || null == b)
- return null == a && null == b;
- if(a.Length != b.Length)
- return false;
- int n = a.Length;
- for(int i = 0; i < n; i++)
- if(!object.Equals(a[i], b[i]))
- return false;
- return true;
- } // end of equal<T>
-
- /// <summary>
- /// Checks whether specified arrays are component-wise equal.
- /// </summary>
- /// <param name="a"> The first array. </param>
- /// <param name="b"> The second array. </param>
- /// <returns> True if they are equal and false if not. </returns>
- /// <remarks> Arrays are equal if either both are null, or both
- /// are non-null, have same rank and sizes, and for all valid indices
- /// elements with the same indices are equal. </remarks>
- public static bool equal(Array a, Array b) {
- if(null == a || null == b)
- return null == a && null == b;
- int[] sza = sizes(a), szb = sizes(b);
- if(!equal(sza, szb))
- return false;
- foreach(int[] p in pointIter(sza)) {
- if(!object.Equals(a.GetValue(p), b.GetValue(p)))
- return false;
- } // end of foreach()
- return true;
- } // end of equal()
-
- /// <summary>
- /// Checks whether the specified arrays contain all their references
- /// equal
- /// </summary>
- /// <typeparam name="T"> The array type </typeparam>
- /// <param name="a"> The first array </param>
- /// <param name="b"> The second array </param>
- /// <returns> True if they do and false if not </returns>
- public static bool equalRef<T>(T[] a, T[] b) where T : class {
- if(null == a || null == b)
- return null == a && null == b;
- if(a.Length != b.Length)
- return false;
- int n = a.Length;
- for(int i = 0; i < n; i++)
- if(a[i] != b[i])
- return false;
- return true;
- } // end of equalRef<T>
-
- /// <summary>
- /// Gets whether all elements of the specified array are equal to
- /// the specified value
- /// </summary>
- /// <typeparam name="T"> The element type </typeparam>
- /// <param name="a"> The array </param>
- /// <param name="b"> The value </param>
- /// <returns> True if it is and false if not </returns>
- public static bool allEqual<T>(T[] a, T b) {
- if(null == a || a.Length == 0)
- return true;
- for(int i = 0; i < a.Length; i++)
- if(!object.Equals(a[i], b))
- return false;
- return true;
- } // end of allEqual<T>()
-
- /// <summary>
- /// Gets whether all elements of the specified array are reference equal to
- /// the specified value
- /// </summary>
- /// <typeparam name="T"> The element type </typeparam>
- /// <param name="a"> The array </param>
- /// <param name="b"> The value </param>
- /// <returns> True if it is and false if not </returns>
- public static bool allEqualRef<T>(T[] a, T b) where T: class {
- if(null == a || a.Length == 0)
- return true;
- for(int i = 0; i < a.Length; i++)
- if(b != a[i])
- return false;
- return true;
- } // end of allEqual<T>()
-
- /// <summary>
- /// Checks whether any of the two elements of the array are the same.
- /// </summary>
- /// <typeparam name="T"> The array type. </typeparam>
- /// <param name="a"> The array. </param>
- /// <returns> True if any two elements of the array are same and
- /// false if not. False is also returned for null and empty arrays as
- /// well as for arrays of one element. Null elements are considered
- /// the same. The equality procedure is considered to be symmetric,
- /// i.e. it is assumed that a[i] equals a[j] iff a[j] equals a[i],
- /// so only one of the checks is performed. </returns>
- public static bool anySame<T>(T[] a) {
- if(null == a || a.Length < 2)
- return false;
- int n = a.Length;
- for(int i = 0; i < n; i++)
- for(int j = i + 1; j < n; j++)
- if(object.Equals(a[i], a[j]))
- return true;
- return false;
- } // end of anySame<T>()
-
- /// <summary>
- /// Gets whether all elements of the array are the same
- /// </summary>
- /// <typeparam name="T"> The array element type </typeparam>
- /// <param name="a"> The array </param>
- /// <returns> True if it is and false if not </returns>
- public static bool allSame<T>(T[] a) {
- if(null == a || a.Length <= 1)
- return true;
- return allEqual<T>(a, a[0]);
- } // end of allSame<T>()
-
- /// <summary>
- /// Gets whether all array elemetns are the same references
- /// </summary>
- /// <typeparam name="T"> The array element type </typeparam>
- /// <param name="a"> The array to check </param>
- /// <returns> True if it is and false if not </returns>
- public static bool allSameRef<T>(T[] a) where T : class {
- if(null == a || a.Length <= 1)
- return true;
- return allEqualRef<T>(a, a[0]);
- } // end of allSameRef<T>()
-
- /// <summary>
- /// Creates an alternative iterator of two arrays of the same length.
- /// If n is the length of both arrays, returns an iterator over a
- /// sequence of 2^n values.
- /// </summary>
- /// <typeparam name="T"> The element type of the array </typeparam>
- /// <param name="a"> The first array </param>
- /// <param name="b"> The second array </param>
- /// <returns> The resulting iterator </returns>
- /// <remarks> The resulting arrays should not be modified </remarks>
- public static IEnumerable<T[]> alterIter<T>(T[] a, T[] b) {
- if(null == a || null == b)
- throw new ArgumentNullException();
- if(a.Length != b.Length)
- throw new ArgumentException();
- int n = a.Length;
- T[] res = new T[n];
- int[] iis = idarr<int>(-1, n); // -1 - no value, 0 - first array,
- // 1 - second array
- int i = 0;
- while(i > -1) {
- if(i < n) {
- switch(iis[i]) {
- case -1: iis[i]++; res[i] = a[i]; i++; break;
- case 0: iis[i]++; res[i] = b[i]; i++; break;
- case 1: iis[i] = -1; i--; break;
- } // end of switch()
- } else {
- i--;
- yield return res;
- } // end of while()
- } // end of while()
- } // end of alterIter<T>()
-
- /// <summary>
- /// Gets the product of all array values and 1 if the array is empty
- /// </summary>
- /// <param name="arr"> The array </param>
- /// <returns> The resulting product </returns>
- public static int prod(params int[] arr) {
- int p = 1;
- foreach(int i in arr)
- p *= i;
- return p;
- } // end of prod()
-
- /// <summary>
- /// Gets the product of all array values and 1 if the array is empty
- /// </summary>
- /// <param name="arr"> The array </param>
- /// <returns> The resulting product </returns>
- public static long prod(params long[] arr) {
- long p = 1;
- foreach(long i in arr)
- p *= i;
- return p;
- } // end of prod()
-
- /// <summary>
- /// Generates a permutation of values which contains
- /// <paramref name="dims"/> dimensions in the beginning,
- /// if <paramref name="last"/> is false, or end, if
- /// <paramref name="last"/> is true, and all other dimensions in other
- /// places
- /// </summary>
- /// <param name="n"> The full rank </param>
- /// <param name="dims"> The numbers of dimensions in question,
- /// in ascending order </param>
- /// <param name="last"> Whether or not to place the dimensions in
- /// question to the end </param>
- /// <returns> The permutation created </returns>
- public static int[] genPermute(int n, int[] dims, bool last) {
- int[] prm = new int[n];
- if(last) {
- for(int i = n - dims.Length; i < n; i++)
- prm[i] = dims[i - n + dims.Length];
- } else {
- for(int i = 0; i < dims.Length; i++)
- prm[i] = dims[i];
- } // end of if()
- // non-dim dimensions
- int j1 = 0, j2 = last ? 0 : dims.Length;
- for(int i = 0; i < n; i++) {
- if(j1 < dims.Length) {
- if(i == dims[j1])
- j1++;
- else
- prm[j2++] = i;
- } else
- prm[j2++] = i;
- } // end of for()
- return prm;
- } // end of genPermute()
-
- /// <summary>
- /// Negates the array component-wise
- /// </summary>
- /// <param name="arr"> The array to negate </param>
- /// <returns> The negated array </returns>
- public static int[] neg(params int[] arr) {
- int n = arr.Length;
- int[] r = new int[n];
- for(int i = 0; i < n; i++)
- r[i] = -arr[i];
- return r;
- } // end of neg()
-
- /// <summary>
- /// Transforms an array into a 2D array of the specified size,
- /// </summary>
- /// <typeparam name="T"> The type of the array to transform </typeparam>
- /// <param name="arr"> The source array </param>
- /// <param name="s"> The size of the resulting 2D array </param>
- /// <returns> The resulting array </returns>
- public static T[,] to2DArray<T>(Array arr, int s) {
- T[,] arr2 = new T[s, s];
- if(arr.Rank == 2) {
- T[,] arr3 = (T[,])arr;
- for(int i0 = 0; i0 < arr.GetLength(0); i0++)
- for(int i1 = 0; i1 < arr.GetLength(1); i1++)
- arr2[i0, i1] = arr3[i0, i1];
- return arr2;
- } // end of if()
- // copy array values
- int i = 0, j = 0;
- foreach(T v in arr) {
- arr2[i, j++] = v;
- if(j == s) {
- i++;
- j = 0;
- } // end of if()
- } // end of foreach()
- return arr2;
- } // end of to2DArray()
-
- /// <summary>
- /// Transforms an array into an m-D array of the specified size
- /// </summary>
- /// <typeparam name="T"> The type of the array to transform </typeparam>
- /// <param name="arr"> The source array </param>
- /// <param name="s"> The sizes of the resulting m-D array </param>
- /// <returns> The resulting array </returns>
- /// <remarks> Only 1 and 2-rank resulting arrays supported.
- /// Also, only square 2d arrays are supported, with first
- /// element of <paramref name="s"/> specifying square dimension
- /// size </remarks>
- public static Array toMDArray<T>(Array arr, int[] s) {
- switch(s.Length) {
- case 1:
- return to1DArray<T>(arr, s[0]);
- case 2:
- return to2DArray<T>(arr, s[0]);
- default:
- throw new NotSupportedException("Only ranks 1 and 2 are supported");
- } // end of switch()
- } // end of toMDArray()
-
- /// <summary>
- /// Linearizes the 2d array and returns it as a linearized 1d array.
- /// All 1d arrays which are elements of the array <paramref name="a"/>
- /// shall be of the same length.
- /// </summary>
- /// <typeparam name="T"> The type of the array element. </typeparam>
- /// <param name="a"> The array to linearize. </param>
- /// <returns> The resulting transposed and linearized array.
- /// res[i * n + j] = a[j][i]</returns>
- public static T[] linearize<T>(T[][] a) {
- int n = a.Length, m = a[0].Length;
- T[] res = new T[m * n];
- for(int j = 0; j < n; j++)
- for(int i = 0; i < m; i++)
- res[i * n + j] = a[j][i];
- return res;
- } // end of transpose<T>()
-
- /// <summary>
- /// Converts from the array of specific dimensionality (only 1 and
- /// 2 are currently supported) to the array of arbitrary number of
- /// dimensions
- /// </summary>
- /// <typeparam name="T"> The array element type </typeparam>
- /// <param name="arr"> The array of 1 or 2 rank </param>
- /// <param name="s"> The size of the first dimension of the
- /// array (only square 2D arrays are supported) </param>
- /// <param name="sizes"> The sizes of the desired array </param>
- /// <returns> The array of desired sizes and rank </returns>
- public static Array fromMDArray<T>(Array arr, int s, int[] sizes) {
- switch(arr.Rank) {
- case 1:
- return from1DArray<T>((T[]) arr, s, sizes);
- case 2:
- return from2DArray<T>((T[,]) arr, s, sizes);
- default:
- throw new NotSupportedException("Only ranks 1 and 2 are supported");
- } // end of switch()
- } // end of fromMDArray()
-
- /// <summary>
- /// Converts the array specified into a 1D array
- /// </summary>
- /// <typeparam name="T"> The type of the array to convert </typeparam>
- /// <param name="arr"> The array to convert </param>
- /// <param name="s"> The desired 1D array size </param>
- /// <returns> The resulting array created </returns>
- public static T[] to1DArray<T>(Array arr, int s) {
- T[] res = new T[s];
- int j = 0;
- foreach(T v in arr)
- res[j++] = v;
- return res;
- } // end of to1DArray<T>()
-
- /// <summary>
- /// Converts the array specified into a 1D array. The size is
- /// supposed equal to the total size of the array being converted.
- /// </summary>
- /// <typeparam name="T"> The type of the array to convert </typeparam>
- /// <param name="arr"> The array to convert </param>
- /// <returns> The resulting array created </returns>
- public static T[] to1DArray<T>(Array arr) {
- return to1DArray<T>(arr, arr.Length);
- } // end of to1DArray<T>()
-
- /// <summary>
- /// Creates a multi-dimensional array from a given 1-dimensional
- /// and returns the array created
- /// </summary>
- /// <typeparam name="T"> The type of the array being transformed </typeparam>
- /// <param name="arr"> The array to transform </param>
- /// <param name="s"> The size of the 1d array (can differ from
- /// the actual size of the array) </param>
- /// <param name="sizes"> The sizes of the resulting array </param>
- /// <returns> The resulting array created </returns>
- public static Array from1DArray<T>(T[] arr, int s, int[] sizes) {
- switch(sizes.Length) {
- case 1: return arr;
- case 2:
- return from1DArrayTo2D<T>(arr, s, sizes);
- case 3:
- return from1DArrayTo3D<T>(arr, s, sizes);
- case 4:
- return from1DArrayTo4D<T>(arr, s, sizes);
- default:
- return from1DArrayToND<T>(arr, s, sizes);
- } // end of switch()
- } // end of from1DArray<T>()
-
- /// <summary>
- /// Creates a 2-dimensional array from a given 1-dimensional
- /// and returns the array created.
- /// </summary>
- /// <typeparam name="T"> The type of the array being transformed </typeparam>
- /// <param name="arr"> The array to transform </param>
- /// <param name="s"> The size of the 1d array (can differ from
- /// the actual size of the array) </param>
- /// <param name="sizes"> The sizes of the resulting array </param>
- /// <returns> The resulting array created </returns>
- public static T[,] from1DArrayTo2D<T>(T[] arr, int s, int[] sizes) {
- int s0 = sizes[0], s1 = sizes[1];
- T[,] res = new T[s0, s1];
- int j = 0;
- for(int i0 = 0; i0 < s0; i0++)
- for(int i1 = 0; i1 < s1; i1++)
- res[i0, i1] = arr[j++];
- return res;
- } // end of from1DArrayTo2D()
-
- /// <summary>
- /// Creates a 3-dimensional array from a given 1-dimensional
- /// and returns the array created.
- /// </summary>
- /// <typeparam name="T"> The type of the array being transformed </typeparam>
- /// <param name="arr"> The array to transform </param>
- /// <param name="s"> The size of the 1d array (can differ from
- /// the actual size of the array) </param>
- /// <param name="sizes"> The sizes of the resulting array </param>
- /// <returns> The resulting array created </returns>
- public static T[,,] from1DArrayTo3D<T>(T[] arr, int s, int[] sizes) {
- int s0 = sizes[0], s1 = sizes[1], s2 = sizes[2];
- T[,,] res = new T[s0, s1, s2];
- int j = 0;
- for(int i0 = 0; i0 < s0; i0++)
- for(int i1 = 0; i1 < s1; i1++)
- for(int i2 = 0; i2 < s2; i2++)
- res[i0, i1, i2] = arr[j++];
- return res;
- } // end of from1DArrayTo3D()
-
- /// <summary>
- /// Creates a 4-dimensional array from a given 1-dimensional
- /// and returns the array created.
- /// </summary>
- /// <typeparam name="T"> The type of the array being transformed </typeparam>
- /// <param name="arr"> The array to transform </param>
- /// <param name="s"> The size of the 1d array (can differ from
- /// the actual size of the array) </param>
- /// <param name="sizes"> The sizes of the resulting array </param>
- /// <returns> The resulting array created </returns>
- public static T[,,,] from1DArrayTo4D<T>(T[] arr, int s, int[] sizes) {
- int s0 = sizes[0], s1 = sizes[1], s2 = sizes[2], s3 = sizes[3];
- T[,,,] res = new T[s0, s1, s2, s3];
- int j = 0;
- for(int i0 = 0; i0 < s0; i0++)
- for(int i1 = 0; i1 < s1; i1++)
- for(int i2 = 0; i2 < s2; i2++)
- for(int i3 = 0; i3 < s3; i3++)
- res[i0, i1, i2, i3] = arr[j++];
- return res;
- } // end of from1DArrayTo4D()
-
- /// <summary>
- /// Creates a multi-dimensional array from a given 1-dimensional
- /// and returns the array created. This is a generic and most
- /// inefficient implementation. For smaller arrays, more efficient
- /// implementations are provided.
- /// </summary>
- /// <typeparam name="T"> The type of the array being transformed </typeparam>
- /// <param name="arr"> The array to transform </param>
- /// <param name="s"> The size of the 1d array (can differ from
- /// the actual size of the array) </param>
- /// <param name="sizes"> The sizes of the resulting array </param>
- /// <returns> The resulting array created </returns>
- public static Array from1DArrayToND<T>(T[] arr, int s, int[] sizes) {
- Array arr2 = Array.CreateInstance(typeof(T), sizes);
- int i = 0;
- foreach(int[] p in pointIter(sizes))
- arr2.SetValue(arr[i++], p);
- return arr2;
- } // end of from1DArrayToND<T>()
-
- /// <summary>
- /// Reads the data from a 2D array into the specified array
- /// </summary>
- /// <typeparam name="T"> The array element type </typeparam>
- /// <param name="arr"> The source 2D array </param>
- /// <param name="s"> The size of the 2D square array </param>
- /// <param name="sizes"> The size of the resulting array </param>
- /// <returns> The resulting array </returns>
- public static Array from2DArray<T>(T[,] arr, int s, int[] sizes) {
- switch(sizes.Length) {
- case 1:
- return from2DArrayTo1D<T>(arr, s, sizes);
- case 2:
- return arr;
- case 3:
- return from2DArrayTo3D<T>(arr, s, sizes);
- case 4:
- return from2DArrayTo4D<T>(arr, s, sizes);
- default:
- return from2DArrayToND<T>(arr, s, sizes);
- } // end of switch()
- } // end of from2DArray<T>()
-
- /// <summary>
- /// Reads the data from the 2D array into a 1D array
- /// </summary>
- /// <typeparam name="T"> The element type </typeparam>
- /// <param name="arr"> The 2D array </param>
- /// <param name="s"> The size of the 2D array </param>
- /// <param name="sizes"> The sizes of the 1D array </param>
- /// <returns> The resulting 1D array </returns>
- public static T[] from2DArrayTo1D<T>(T[,] arr, int s, int[] sizes) {
- int n = sizes[0];
- T[] arr2 = new T[n];
- int i = 0, j = 0;
- for(int p = 0; p < n; p++) {
- arr2[p] = arr[i, j++];
- if(j == s) {
- i++;
- j = 0;
- } // end of if()
- } // end of for()
- return arr2;
- } // end of from2DArrayTo1D()
-
- /// <summary>
- /// Converts a 2D array representation into a 3D array
- /// </summary>
- /// <typeparam name="T"> The array type </typeparam>
- /// <param name="arr"> The array to convert </param>
- /// <param name="s"> The size of the 2D array along one
- /// of the dimensions </param>
- /// <param name="sizes"> The sizes of the 3D array </param>
- /// <returns> The 3D array created </returns>
- public static T[, ,] from2DArrayTo3D<T>(T[,] arr, int s, int[] sizes) {
- int n0 = sizes[0], n1 = sizes[1], n2 = sizes[2];
- T[,,] arr2 = new T[n0, n1, n2];
- int i = 0, j = 0;
- for(int p0 = 0; p0 < n0; p0++)
- for(int p1 = 0; p1 < n1; p1++)
- for(int p2 = 0; p2 < n2; p2++) {
- arr2[p0, p1, p2] = arr[i, j++];
- if(j == s) {
- i++;
- j = 0;
- } // end of if()
- } // end of for()
- return arr2;
- } // end of from2DArrayTo3D<T>()
-
- /// <summary>
- /// Converts a 2D array representation into a 4D array
- /// </summary>
- /// <typeparam name="T"> The array type </typeparam>
- /// <param name="arr"> The array to convert </param>
- /// <param name="s"> The size of the 2D array along one
- /// of the dimensions </param>
- /// <param name="sizes"> The sizes of the 4D array </param>
- /// <returns> The 4D array created </returns>
- public static T[,, ,] from2DArrayTo4D<T>(T[,] arr, int s, int[] sizes) {
- int n0 = sizes[0], n1 = sizes[1], n2 = sizes[2], n3 = sizes[3];
- T[, , ,] arr2 = new T[n0, n1, n2, n3];
- int i = 0, j = 0;
- for(int p0 = 0; p0 < n0; p0++)
- for(int p1 = 0; p1 < n1; p1++)
- for(int p2 = 0; p2 < n2; p2++)
- for(int p3 = 0; p3 < n3; p3++) {
- arr2[p0, p1, p2, p3] = arr[i, j++];
- if(j == s) {
- i++;
- j = 0;
- } // end of if()
- } // end of for()
- return arr2;
- } // end of from2DArrayTo4D<T>()
-
- /// <summary>
- /// Reads the data from the 2D array into an ND array
- /// </summary>
- /// <typeparam name="T"> The element type </typeparam>
- /// <param name="arr"> The 2D array </param>
- /// <param name="s"> The size of the 2D array </param>
- /// <param name="sizes"> The sizes of the ND array </param>
- /// <returns> The resulting ND array </returns>
- public static Array from2DArrayToND<T>(T[,] arr, int s, int[] sizes) {
- Array arr2 = Array.CreateInstance(typeof(T), sizes);
- int i = 0, j = 0;
- foreach(int[] p in pointIter(sizes)) {
- arr2.SetValue(arr[i, j++], p);
- if(j == s) {
- i++;
- j = 0;
- } // end of if()
- } // end of for()
- return arr2;
- } // end of from2DArrayToND()
-
- /// <summary>
- /// Checks whether the arrays have equal length and whether the predicate
- /// is valid for both of them
- /// </summary>
- /// <typeparam name="T1"> The type of the first array </typeparam>
- /// <typeparam name="T2"> The type of the second array </typeparam>
- /// <param name="arr1"> The first array </param>
- /// <param name="arr2"> The second array </param>
- /// <param name="prd"> The predicate to check </param>
- /// <returns> True iff either both <paramref name="arr1"/>
- /// and <paramref name="arr2"/> are null or both of them have equal length
- /// and for each pair of their respective elements the predicate
- /// <paramref name="prd"/> holds, i.e., returns true </returns>
- public static bool allTrue<T1, T2>(T1[] arr1, T2[] arr2, DoublePred<T1, T2> prd) {
- // check for null
- if(arr1 == null || arr2 == null) {
- return arr1 == null && arr2 == null;
- }
- if(prd == null)
- throw new ArgumentNullException();
- if(arr1.Length != arr2.Length)
- return false;
- int n = arr1.Length;
- for(int i = 0; i < n; i++)
- if(!prd(arr1[i], arr2[i]))
- return false;
- return true;
- } // end of allTrue<T1, T2>
-
- /// <summary>
- /// Checks whether the array are compatible and the predicate is true
- /// for each pair of elements in the arrays.
- /// </summary>
- /// <typeparam name="T1"> The type of the first array element. </typeparam>
- /// <typeparam name="T2"> The type of the second array element. </typeparam>
- /// <param name="a"> The first array. </param>
- /// <param name="b"> The second array. </param>
- /// <param name="prd"> The predicate to check. </param>
- /// <returns> True if either both arrays are null, or they are non-null,
- /// have equal ranks and sizes, and for each pair of corresponding elements,
- /// the predicate holds. Otherwise, returns false. </returns>
- public static bool allTrue<T1, T2>(Array a, Array b,
- DoublePred<T1, T2> prd) {
- if(null == a || null == b)
- return null == a && null == b;
- int[] sza = sizes(a), szb = sizes(b);
- if(!equal(sza, szb))
- return false;
- foreach(int[] p in pointIter(sza)) {
- if(!prd((T1)a.GetValue(p), (T2)b.GetValue(p)))
- return false;
- } // end of foreach()
- return true;
- } // end of allTrue<T1, T2>()
-
- /// <summary>
- /// Concatenates the first array with the second array
- /// </summary>
- /// <typeparam name="T"> The type of the arrays being concatenated </typeparam>
- /// <param name="arr1"> The first array to be concatenated </param>
- /// <param name="arr2"> The second array to be concatenated </param>
- /// <returns> The result of concatenation </returns>
- public static T[] con<T>(T[] arr1, T[] arr2) {
- if(arr1 == null)
- return arr2;
- if(arr2 == null)
- return arr1;
- int l1 = arr1.Length, l2 = arr2.Length;
- int l = l1 + l2;
- T[] res = new T[l];
- int i = 0;
- for(; i < l1; i++)
- res[i] = arr1[i];
- for(; i < l; i++)
- res[i] = arr2[i - l1];
- return res;
- }
-
- /// <summary>
- /// Concatenates any number of arrays of the same type specified
- /// </summary>
- /// <typeparam name="T"> The element type of the arrays to concatenate </typeparam>
- /// <param name="arrs"> The arrays to concatenate </param>
- /// <returns> The result of concatenation </returns>
- public static T[] con<T>(params T[][] arrs) {
- if(arrs == null)
- return null;
- if(arrs.Length == 0)
- return new T[] { };
- //if(Array.TrueForAll<T[]>(arrs, delegate(T[] a) { return a == null; }))
- // return null;
- if(null == arrs[0] && allEqualRef<T[]>(arrs, null))
- return null;
- int n = 0;
- for(int i = 0; i < arrs.Length; i++)
- n += arrs[i].Length;
- T[] res = new T[n];
- int k = 0;
- for(int i = 0; i < arrs.Length; i++)
- for(int j = 0; j < arrs[i].Length; j++)
- res[k++] = arrs[i][j];
- return res;
- } // end of con<T>()
-
- /// <summary>
- /// Adds an element to the end of the array
- /// </summary>
- /// <typeparam name="T"> The type of the array element </typeparam>
- /// <param name="arr"> The array to concatenate </param>
- /// <param name="el"> The element to concatenate </param>
- /// <returns> The resulting array </returns>
- public static T[] con<T>(T[] arr, T el) {
- return con<T>(arr, new T[] { el });
- } // end of con<T>
-
- /// <summary>
- /// Adds an element to the beginning of the array
- /// </summary>
- /// <typeparam name="T"> The type of the array element </typeparam>
- /// <param name="el"> The element to concatenate </param>
- /// <param name="arr"> The array to concatenate </param>
- /// <returns> The resulting array </returns>
- public static T[] con<T>(T el, T[] arr) {
- return con<T>(new T[] { el }, arr);
- } // end of con<T>
-
- /// <summary>
- /// Indexes the array with an array of indices and returns the result of the
- /// indexing
- /// </summary>
- /// <typeparam name="T"> The type of the array to index </typeparam>
- /// <param name="arr"> The array to index </param>
- /// <param name="inds"> The indices of the elements to retrieve </param>
- /// <returns> The list of indices for indexing </returns>
- public static T[] index<T>(T[] arr, params int[] inds) {
- List<T> l = new List<T>();
- if(inds == null)
- return l.ToArray();
- if(arr == null) {
- if(inds == null || inds.Length == 0)
- return l.ToArray();
- throw new ArgumentNullException();
- }
- foreach(int i in inds)
- l.Add(arr[i]);
- return l.ToArray();
- } // end of index()
-
- /// <summary>
- /// Creates a new array which contains original values except
- /// those specified in <paramref name="inds"/>; they are removed
- /// </summary>
- /// <typeparam name="T"> The type of the array element </typeparam>
- /// <param name="arr"> The source array </param>
- /// <param name="inds"> The indices to be except </param>
- /// <returns> The resulting array </returns>
- public static T[] indexExcept<T>(T[] arr, params int[] inds) {
- int rn = arr.Length - inds.Length;
- T[] ra = new T[rn];
- // current index to inds array
- int k = 0;
- // current index to resulting array
- int j = 0;
- for(int i = 0; i < arr.Length; i++) {
- if(k >= inds.Length || inds[k] != i)
- ra[j++] = arr[i];
- else
- k++;
- } // end of for()
- return ra;
- } // end of indexExcept<T>()
-
- /// <summary>
- /// Gets the indices of the array given the single cumulative index.
- /// </summary>
- /// <param name="index"> The cumulative index of the array </param>
- /// <param name="cumSizes"> The cumulative sizes of the array. The
- /// last of it equals to 1, the next-to-last to cumSizes[cumSizes.Length - 1] *
- /// sizes[cumSizes.length - 1], etc. </param>
- /// <returns> The resulting set of indices </returns>
- public static int[] indices(int index, int[] cumSizes) {
- int n = cumSizes.Length;
- int[] inds = new int[n];
- int j = index;
- for(int i = 0; i < n; i++) {
- inds[i] = j / cumSizes[i];
- j %= cumSizes[i];
- }
- return inds;
- } // end of indices()
-
- /// <summary>
- /// Creates the array of cumulative sizes from the array of sizes
- /// </summary>
- /// <param name="sizes"> The array of sizes </param>
- /// <returns> The array of cumulative sizes </returns>
- /// <remarks> When it is created, it is assumed that the first index in
- /// the array changes the slowest </remarks>
- public static int[] cumSizes(int[] sizes) {
- int n = sizes.Length;
- int[] cs = new int[n];
- cs[n - 1] = 1;
- for(int i = n - 2; i >= 0; i--)
- cs[i] = cs[i + 1] * sizes[i + 1];
- return cs;
- }
-
- /// <summary>
- /// Creates a tail from an array starting from the specified element
- /// </summary>
- /// <typeparam name="T"> The type of the array element </typeparam>
- /// <param name="arr"> The array from which to create a tail </param>
- /// <param name="start"> The start element of the tail </param>
- /// <returns> The tail created </returns>
- public static T[] tail<T>(T[] arr, int start) {
- if(start <= 0)
- return arr;
- if(start >= arr.Length)
- throw new IndexOutOfRangeException();
- int nl = arr.Length - start;
- T[] res = new T[nl];
- for(int i = 0; i < nl; i++)
- res[i] = arr[start + i];
- return res;
- }
-
- /// <summary>
- /// Gets the array of sizes of the array.
- /// </summary>
- /// <param name="arr"> The array for which to get the sizes. </param>
- /// <returns> The array of sizes of the array, staring from the one
- /// along which changes the slowest (i.e., the first). Returns null for
- /// null arrays. </returns>
- public static int[] sizes(Array arr) {
- if(null == arr)
- return null;
- int n = arr.Rank;
- int[] sz = new int[n];
- for(int i = 0; i < n; i++)
- sz[i] = arr.GetLength(i);
- return sz;
- }
-
- /// <summary>
- /// Creates a 1D array of the specified type and of specified size with all
- /// elements equal to a specified value
- /// </summary>
- /// <typeparam name="T"> The type of the array to create </typeparam>
- /// <param name="val"> The value of the array element </param>
- /// <param name="size"> The length of the array to create </param>
- /// <returns> The array created </returns>
- public static T[] idarr<T>(T val, int size) {
- if(size < 0)
- throw new ArgumentOutOfRangeException();
- T[] arr = new T[size];
- for(int i = 0; i < arr.Length; i++)
- arr[i] = val;
- return arr;
- }
-
- /// <summary>
- /// Transforms two arrays of values into a single array of values
- /// </summary>
- /// <typeparam name="T1"> The type of the first array of values </typeparam>
- /// <typeparam name="T2"> The type of the second array of values </typeparam>
- /// <typeparam name="T3"> The type of the resulting array of values </typeparam>
- /// <param name="arr1"> The first array of values </param>
- /// <param name="arr2"> The second array of values </param>
- /// <param name="trs"> The transform to apply </param>
- /// <returns> The resulting array of values </returns>
- public static T3[] map2<T1, T2, T3>(T1[] arr1, T2[] arr2, Transform<T1, T2, T3>
- trs) {
- // check for nulls
- if(arr1 == null || arr2 == null) {
- if(arr1 == null && arr2 == null)
- return null;
- else
- throw new ArgumentNullException();
- }
- if(trs == null)
- throw new ArgumentNullException();
- if(arr1.Length != arr2.Length)
- throw new ArgumentException();
- int n = arr1.Length;
- T3[] res = new T3[n];
- for(int i = 0; i < n; i++)
- res[i] = trs(arr1[i], arr2[i]);
- return res;
- }
-
- /// <summary>
- /// Performs the reduction of the specified array by the specified function
- /// </summary>
- /// <typeparam name="T"> The type of the array to reduce </typeparam>
- /// <param name="arr"> The array being reduced </param>
- /// <param name="red"> The reducing function </param>
- /// <returns> The result of the reduciton </returns>
- public static T reduce<T>(T[] arr, Transform<T, T, T> red) {
- if(null == arr || null == red)
- throw new ArgumentNullException();
- if(arr.Length == 0)
- return default(T);
- if(arr.Length == 1)
- return arr[0];
- T res = arr[0];
- for(int i = 1; i < arr.Length; i++)
- res = red(res, arr[i]);
- return res;
- }
-
- /// <summary>
- /// Converts an array of arbitrary rank from one type to another.
- /// </summary>
- /// <typeparam name="TI"> The input type of the array. </typeparam>
- /// <typeparam name="TO"> The output type of the array. </typeparam>
- /// <param name="a"> The array to convert. </param>
- /// <param name="conv"> The converter delegate. </param>
- /// <returns> The resulting array. </returns>
- public static Array map<TI, TO>(Array a, Converter<TI, TO> conv) {
- if(a.Rank == 1)
- return Array.ConvertAll<TI, TO>((TI[])a, conv);
- int[] sz = sizes(a);
- Array newa = Array.CreateInstance(typeof(TO), sz);
- foreach(int[] p in pointIter(sz))
- newa.SetValue(conv((TI)a.GetValue(p)), p);
- return newa;
- } // end of map()
-
- /// <summary>
- /// Gets the head of the specified array
- /// </summary>
- /// <param name="arr"> The array from which to get the head </param>
- /// <param name="end"> The index of the last element to be included in
- /// the head array </param>
- /// <returns> The head of the array </returns>
- public static T[] head<T>(T[] arr, int end) {
- if(null == arr)
- return null;
- if(end < 0)
- throw new IndexOutOfRangeException();
- if(end >= arr.Length)
- return arr;
- T[] res = new T[end + 1];
- for(int i = 0; i <= end; i++)
- res[i] = arr[i];
- return res;
- }
-
- /// <summary>
- /// Accepts the list of arrays and returns
- /// their union
- /// </summary>
- /// <typeparam name="T"> The type of the arrays to unite </typeparam>
- /// <param name="arr"> The arrays to unite </param>
- /// <returns> The union of the arrays </returns>
- /// <remarks> The result does not have any repeating elements; that is,
- /// even if a single array is passed, it has its repeating elements
- /// removed </remarks>
- public static T[] union<T>(params T[][] arr) {
- if(null == arr || arr.Length == 0)
- return new T[] { };
- //List<T> l = new List<T>();
- //Set<T> s = new Set<T>();
- //foreach(T[] a in arr) {
- // if(null == a)
- // continue;
- // foreach(T el in a)
- // if(!s.Contains(el)) {
- // s.Add(el);
- // l.Add(el);
- // }
- //}
- //return l.ToArray();
- List<T> l = new List<T>(arr.Length * arr[0].Length);
- for(int i = 0; i < arr[0].Length; i++) {
- T v = arr[0][i];
- if(l.IndexOf(v) == -1)
- l.Add(v);
- } // end of for()
- for(int i = 1; i < arr.Length; i++)
- for(int j = 0; j < arr[i].Length; j++) {
- T v = arr[i][j];
- if(l.IndexOf(v) == -1)
- l.Add(v);
- } // end of for()
- return l.ToArray();
- } // end of union()
-
- /// <summary>
- /// Accepts two arrays and returns their difference
- /// </summary>
- /// <typeparam name="T"> The type of the array </typeparam>
- /// <param name="arr1"> The first array </param>
- /// <param name="arr2"> The second array </param>
- /// <returns> The difference of the first and second arrays </returns>
- public static T[] diff<T>(T[] arr1, T[] arr2) {
- //if(null == arr1 || null == arr2)
- // throw new ArgumentNullException();
- //List<T> l = new List<T>();
- //Set<T> s = new Set<T>(arr1).Difference(new Set<T>(arr2));
- //Set<T> s1 = new Set<T>(); // for there be no identical elements
- //foreach(T el in arr1)
- // if(s.Contains(el) && !s1.Contains(el)) {
- // s1.Add(el);
- // l.Add(el);
- // }
- //return l.ToArray();
- int n = arr1.Length;
- List<T> l = new List<T>(n);
- for(int i = 0; i < arr1.Length; i++) {
- T val = arr1[i];
- if(Array.IndexOf(arr2, val) == -1 && l.IndexOf(val) == -1)
- l.Add(val);
- } // end of for()
- return l.ToArray();
- } // end of diff();
-
- /// <summary>
- /// Gets the array containing integer span of data between a and b
- /// </summary>
- /// <param name="a"> The start of the span </param>
- /// <param name="b"> The end of the span </param>
- /// <returns> The span created or null if none </returns>
- public static int[] span(int a, int b) {
- if(b < a) return null;
- int n = b - a + 1;
- int[] arr = new int[n];
- for(int i = a; i <= b; i++) arr[i - a] = i;
- return arr;
- } // end of span()
-
- /// <summary>
- /// Gets the floating-point
- /// array containing integer span of data between a and b
- /// </summary>
- /// <param name="a"> The start of the span </param>
- /// <param name="b"> The end of the span </param>
- /// <returns> The span created or null if none </returns>
- public static float[] spanFloat(int a, int b) {
- if(b < a) return null;
- int n = b - a + 1;
- float[] arr = new float[n];
- for(int i = a; i <= b; i++) arr[i - a] = i;
- return arr;
- } // end of spanFloat()
-
- /// <summary>
- /// Iterates over a rectangular set of integer points, starting from
- /// (0, ..., 0) and ending with (sizes[0]-1, ..., sizes[n-1]-1), with
- /// first index chaning the slowest. In case null or zero-length array
- /// is passed, returns a single zero-length array
- /// </summary>
- /// <param name="sizes"> The limits of the domain over which to
- /// iterate </param>
- /// <returns> The iterator over the point domain </returns>
- public static IEnumerable<int[]> pointIter(int[] sizes) {
- if(null == sizes || sizes.Length == 0) {
- yield return new int[0];
- yield break;
- } else {
- int n = sizes.Length;
- int[] vals = idarr<int>(-1, n);
- int ptr = 0;
- while(ptr != -1) {
- if(ptr == n) {
- yield return (int[])vals.Clone();
- ptr--;
- } else {
- vals[ptr]++;
- if(vals[ptr] == sizes[ptr]) {
- vals[ptr] = -1;
- ptr--;
- } else {
- ptr++;
- } // end of if()-else
- } // end of if()-else
- } // end of while()
- } // end of if()-else
- } // end of pointIter()
-
- /// <summary>
- /// Creates an array of <paramref name="size"/> elements, all of
- /// which are equal to <paramref name="val"/>, except for element
- /// with index <paramref name="pos"/>, which is equal to
- /// <paramref name="diffVal"/>
- /// </summary>
- /// <typeparam name="T"> The type of the element & array </typeparam>
- /// <param name="size"> The size of the resulting array </param>
- /// <param name="pos"> The position in the array which shall differ </param>
- /// <param name="val"> The value of the array element </param>
- /// <param name="diffVal"> The different value of the single element </param>
- /// <returns> The array created </returns>
- public static T[] singleDiff<T>(int size, int pos, T val, T diffVal) {
- T[] a = idarr<T>(val, size);
- a[pos] = diffVal;
- return a;
- } // end of singleDiff<T>()
-
- /// <summary>
- /// Evaluates the dot product of two integer arrays
- /// </summary>
- /// <param name="a1"> The first array </param>
- /// <param name="a2"> The second array </param>
- /// <returns> The dot product of two arrays </returns>
- public static int dot(int[] a1, int[] a2) {
- int n = a1.Length;
- if(a2.Length != n)
- throw new ArgumentException();
- int r = 0;
- for(int i = 0; i < n; i++)
- r += a1[i] * a2[i];
- return r;
- } // end of dot()
-
- /// <summary>
- /// Assigns values of <paramref name="src"/> to <paramref name="tgt"/>,
- /// so that each element of <paramref name="src"/> is assigned to the
- /// <paramref name="inds"/> position with respective index of
- /// <paramref name="tgt"/>. If there are several candidates to the
- /// same position, any of them can be assigned.
- /// </summary>
- /// <typeparam name="T"> The type of the array </typeparam>
- /// <param name="tgt"> The target array </param>
- /// <param name="src"> The source array </param>
- /// <param name="inds"> The indices at which to assign </param>
- public static void arrass<T>(T[] tgt, T[] src, int[] inds) {
- int n = src.Length;
- if(inds.Length != n)
- throw new ArgumentException("Source and indices lengths do not match");
- for(int i = 0; i < n; i++) tgt[inds[i]] = src[i];
- } // end of arrass<T>
-
- /// <summary>
- /// Removes duplicates in the array
- /// </summary>
- /// <param name="arr"> The array from which to remove duplicates </param>
- /// <returns> The array with all duplicates removed </returns>
- public static T[] removeDups<T>(T[] arr) {
- List<T> l = new List<T>();
- Set<T> s = new Set<T>();
- foreach(T t in arr)
- if(!s.Contains(t)) {
- s.Add(t);
- l.Add(t);
- } // end of if()
- return l.ToArray();
- } // end of removeDups()
-
- /// <summary>
- /// Gets the indices of objects of <paramref name="arr2"/> with which
- /// they are present in <paramref name="arr1"/>
- /// </summary>
- /// <typeparam name="T"> The array type </typeparam>
- /// <param name="arr1"> The first array </param>
- /// <param name="arr2"> The second array </param>
- /// <returns> The array of indices </returns>
- public static int[] indicesOf<T>(T[] arr1, T[] arr2) {
- int n = arr2.Length;
- int[] inds = new int[n];
- for(int i = 0; i < n; i++)
- inds[i] = Array.IndexOf<T>(arr1, arr2[i]);
- return inds;
- } // end of indicesOf<T>
-
- /// <summary>
- /// Given an array and a predicate, finds indices of all elements for
- /// which the predicate evaluates to true
- /// </summary>
- /// <typeparam name="T"> The type of the array element </typeparam>
- /// <param name="arr1"> The array </param>
- /// <param name="p"> The predicate </param>
- /// <returns> The array of indices for which the predicate evaluates
- /// to true </returns>
- public static int[] indicesOf<T>(T[] arr1, Predicate<T> p) {
- List<int> l = new List<int>();
- for(int i = 0; i < arr1.Length; i++)
- if(p(arr1[i])) l.Add(i);
- return l.ToArray();
- } // end of indicesOf()
-
- /// <summary>
- /// Reverses the given array
- /// </summary>
- /// <typeparam name="T"> The type of the array to reverse </typeparam>
- /// <param name="arr"> The array to reverse </param>
- /// <returns> The reversed array </returns>
- /// <remarks> Reversing a null array returns null. </remarks>
- public static T[] reverse<T>(T[] arr) {
- if(null == arr)
- return null;
- int n = arr.Length;
- T[] arr2 = new T[n];
- for(int i = 0; i < n; i++)
- arr2[i] = arr[n - i - 1];
- return arr2;
- } // end of reverse<T>()
-
- /// <summary>
- /// Given the keys and values, makes a map. The number of keys
- /// shall be the same as the number of values, and the keys shall not
- /// duplicate itself
- /// </summary>
- /// <typeparam name="TK"> The type of the key </typeparam>
- /// <typeparam name="TV"> The type of the value </typeparam>
- /// <param name="keys"> The keys </param>
- /// <param name="vals"> The values </param>
- /// <returns> The dictionary created </returns>
- public static Dictionary<TK, TV> makeMap<TK, TV>(TK[] keys, TV[] vals) {
- if(keys.Length != vals.Length)
- throw new ArgumentException("Length of keys and values " +
- "must be the same");
- Di…
Large files files are truncated, but you can click here to view the full file