//\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\
// CommonHelpers satellite library | Author: Sergei Y.Kitáev
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
using System;

#if !WASM
namespace CommonHelpers {
#else
namespace CommonHelpers.WASM {
#endif

//**************************************************************************************************
partial class HArray2D {
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

public static T StrictMin<T>(T[,] array,int dimension,int subarrayIdx)
   where T: IComparable
{
   return StrictMinOrMax( array, dimension, subarrayIdx, HMinOrMax.Min, null, null );
}

public static T StrictMin<T>(T[,] array,int dimension,int subarrayIdx,int? startIdx)
   where T: IComparable
{
   return StrictMinOrMax( array, dimension, subarrayIdx, HMinOrMax.Min, startIdx, null );
}

public static T StrictMin<T>(T[,] array,int dimension,int subarrayIdx,int? startIdx,int? count)
   where T: IComparable
{
   return StrictMinOrMax( array, dimension, subarrayIdx, HMinOrMax.Min, startIdx, count );
}

//--------------------------------------------------------------------------------------------------

public static T StrictMax<T>(T[,] array,int dimension,int subarrayIdx)
   where T: IComparable
{
   return StrictMinOrMax( array, dimension, subarrayIdx, HMinOrMax.Max, null, null );
}

public static T StrictMax<T>(T[,] array,int dimension,int subarrayIdx,int? startIdx)
   where T: IComparable
{
   return StrictMinOrMax( array, dimension, subarrayIdx, HMinOrMax.Max, startIdx, null );
}

public static T StrictMax<T>(T[,] array,int dimension,int subarrayIdx,int? startIdx,int? count)
   where T: IComparable
{
   return StrictMinOrMax( array, dimension, subarrayIdx, HMinOrMax.Max, startIdx, count );
}

//==================================================================================================

public static int? StrictIndexOfMin<T>(T[,] array,int dimension,int subarrayIdx)
   where T: IComparable
{
   return StrictIndexOfMinOrMax( array, dimension, subarrayIdx, HMinOrMax.Min, null, null );
}

public static int? StrictIndexOfMin<T>(T[,] array,int dimension,int subarrayIdx,int? startIdx)
   where T: IComparable
{
   return StrictIndexOfMinOrMax( array, dimension, subarrayIdx, HMinOrMax.Min, startIdx, null );
}

public static int? StrictIndexOfMin<T>( T[,] array, int dimension, int subarrayIdx,
                                        int? startIdx, int? count )
   where T: IComparable
{
   return StrictIndexOfMinOrMax( array, dimension, subarrayIdx, HMinOrMax.Min, startIdx, count );
}

//--------------------------------------------------------------------------------------------------

public static int? StrictIndexOfMax<T>(T[,] array,int dimension,int subarrayIdx)
   where T: IComparable
{
   return StrictIndexOfMinOrMax( array, dimension, subarrayIdx, HMinOrMax.Max, null, null );
}

public static int? StrictIndexOfMax<T>(T[,] array,int dimension,int subarrayIdx,int? startIdx)
   where T: IComparable
{
   return StrictIndexOfMinOrMax( array, dimension, subarrayIdx, HMinOrMax.Max, startIdx, null );
}

public static int? StrictIndexOfMax<T>( T[,] array, int dimension, int subarrayIdx,
                                        int? startIdx, int? count )
   where T: IComparable
{
   return StrictIndexOfMinOrMax( array, dimension, subarrayIdx, HMinOrMax.Max, startIdx, count );
}

//==================================================================================================

static T StrictMinOrMax<T>( T[,] array, int dimension, int subarrayIdx,
                            HMinOrMax minmax, int? startIdx, int? count )
   where T: IComparable
{
   int? index;
   T value = GetMinOrMax( array, dimension, subarrayIdx, minmax, startIdx, count, out index );
   if (index==null)
      throw new HEmptySetException();
   return value;
}

//--------------------------------------------------------------------------------------------------

static int? StrictIndexOfMinOrMax<T>( T[,] array, int dimension, int subarrayIdx,
                                      HMinOrMax minmax, int? startIdx, int? count )
   where T: IComparable
{
   int? index;
   GetMinOrMax( array, dimension, subarrayIdx, minmax, startIdx, count, out index );
   if (index==null)
      throw new HEmptySetException();
   return index;
}

//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
} // HArray2D
//**************************************************************************************************

} // CommonHelpers (.WASM)
