/// <summary> /// Multidimensional scaling/PCoA: transform distances to points in a coordinate system. /// </summary> /// <param name="input">A matrix of pairwise distances. Zero indicates identical objects.</param> /// <returns>A matrix, the columns of which are coordinates in the nth dimension. /// The rows are in the same order as the input.</returns> public static ILArray <double> Scale(ILArray <double> input) { int n = input.Length; ILArray <double> p = ILMath.eye <double>(n, n) - ILMath.repmat(1.0 / n, n, n); ILArray <double> a = -.5 * ILMath.multiplyElem(input, input); ILArray <double> b = ILMath.multiply(p, a, p); ILArray <complex> V = ILMath.empty <complex>(); ILArray <complex> E = ILMath.eig((b + b.T) / 2, V); ILArray <int> i = ILMath.empty <int>(); ILArray <double> e = ILMath.sort(ILMath.diag(ILMath.real(E)), i); e = ILMath.flipud(e); i = ILMath.toint32(ILMath.flipud(ILMath.todouble(i))); ILArray <int> keep = ILMath.empty <int>(); for (int j = 0; j < e.Length; j++) { if (e[j] > 0.000000001) { keep.SetValue(j, keep.Length); } } ILArray <double> Y; if (ILMath.isempty(keep)) { Y = ILMath.zeros(n, 1); } else { Y = ILMath.zeros <double>(V.S[0], keep.Length); for (int j = 0; j < keep.Length; j++) { Y[ILMath.full, j] = ILMath.todouble(-V[ILMath.full, i[keep[j]]]); } Y = ILMath.multiply(Y, ILMath.diag(ILMath.sqrt(e[keep]))); } ILArray <int> maxind = ILMath.empty <int>(); ILMath.max(ILMath.abs(Y), maxind, 0); int d = Y.S[1]; ILArray <int> indices = maxind + ILMath.toint32(ILMath.array <int>(SteppedRange(0, n, (d - 1) * n))); ILArray <double> colsign = ILMath.sign(Y[indices]); for (int j = 0; j < Y.S[1]; j++) { Y[ILMath.full, j] = Y[ILMath.full, j] * colsign[j]; } return(Y); }
/// <summary> /// Elementwise multiplication /// </summary> /// <param name="in1">first factor</param> /// <param name="in2">second factor</param> /// <returns>New ILArray of same type as the first input array of the same size than in1 and in2 holding /// the elementwise products of both arrays</returns> /// <remarks>This operator is overloaded for all numeric datatypes: <![CDATA[ILArray<double>,ILArray<float>,ILArray<complex>,ILArray<fcomplex>,ILArray<byte>,ILArray<char>,ILArray<Int16>,ILArray<Int32>,ILArray<Int64>,ILArray<UInt16>,ILArray<UInt32>,ILArray<UInt64>]]></remarks> public static ILArray <byte> operator *(ILArray <byte> in1, ILArray <BaseT> in2) { if (false) { } else if (in2 is ILArray <byte> ) { return(ILMath.multiplyElem(in1, in2 as ILArray <byte>)); } throw new Exception("Operator * not defined for " + in1.GetType().Name + " and " + in2.GetType().Name); }
/// <summary> /// Elementwise multiplication /// </summary> /// <param name="in1">first factor</param> /// <param name="in2">second factor</param> /// <returns>New ILArray of same type as the first input array of the same size than in1 and in2 holding /// the elementwise products of both arrays</returns> /// <remarks>This operator is overloaded for all numeric datatypes: <![CDATA[ILArray<double>,ILArray<float>,ILArray<complex>,ILArray<fcomplex>,ILArray<byte>,ILArray<char>,ILArray<Int16>,ILArray<Int32>,ILArray<Int64>,ILArray<UInt16>,ILArray<UInt32>,ILArray<UInt64>]]></remarks> public static /*!HC:outArr1*/ ILArray <double> operator *(/*!HC:inCls1*/ ILArray <double> in1, ILArray <BaseT> in2) { if (false) { } else if (in2 is /*!HC:inCls2*/ ILArray <double> ) { return(ILMath.multiplyElem(in1, in2 as /*!HC:inCls2*/ ILArray <double>)); } throw new Exception("Operator * not defined for " + in1.GetType().Name + " and " + in2.GetType().Name); }