コード例 #1
0
        /// <summary>
        /// Applys the function (delegate) given to all elements of the storage
        /// </summary>
        /// <param name="inArray">storage array to be apply the function to</param>
        /// <param name="operation">operation to apply to the elements of inArray. This
        /// acts like a function pointer.</param>
        /// <returns>new ILArray<double> with result</returns>
        /// <remarks> the values of inArray will not be altered.</remarks>
        private static ILLogicalArray LogicalUnaryDoubleOperator(ILArray <double> inArray, ILApplyLogical_Double operation)
        {
            ILDimension inDim = inArray.Dimensions;

            byte[] retByteArr;
            // build ILDimension
            int newLength = inDim.NumberOfElements;

            retByteArr = new byte[newLength];
            int leadDim    = 0;
            int leadDimLen = inDim[0];

            if (inArray.IsReference)
            {
                #region Reference storage
                // walk along the longest dimension (for performance reasons)
                for (int i = 1; i < inDim.NumberOfDimensions; i++)
                {
                    if (leadDimLen < inDim[i])
                    {
                        leadDimLen = inDim[i];
                        leadDim    = i;
                    }
                }
                ILIndexOffset idxOffset = inArray.m_indexOffset;
                int           incOut    = inDim.SequentialIndexDistance(leadDim);
                // ========================  REFERENCE double Storage ===========
                if (inArray.IsMatrix)
                {
                    #region Matrix
                    ////////////////////////////   MATRIX   ////////////////////
                    int secDim = (leadDim + 1) % 2;
                    unsafe
                    {
                        fixed(int *leadDimStart = idxOffset[leadDim],
                              secDimStart       = idxOffset[secDim])
                        {
                            fixed(byte *pOutArr = retByteArr)
                            {
                                fixed(double *pInArr = inArray.m_data)
                                {
                                    byte *  tmpOut     = pOutArr;
                                    double *tmpIn      = pInArr;
                                    byte *  tmpOutEnd  = pOutArr + inDim.NumberOfElements - 1;
                                    int *   secDimEnd  = secDimStart + idxOffset[secDim].Length;
                                    int *   secDimIdx  = secDimStart;
                                    int *   leadDimIdx = leadDimStart;
                                    int *   leadDimEnd = leadDimStart + idxOffset[secDim].Length;;

                                    while (secDimIdx < secDimEnd)
                                    {
                                        tmpIn      = pInArr + *secDimIdx++;
                                        leadDimIdx = leadDimStart;
                                        while (leadDimIdx < leadDimEnd)
                                        {
                                            *tmpOut = operation(*(tmpIn + *leadDimIdx++));
                                            tmpOut += incOut;
                                        }
                                        if (tmpOut > tmpOutEnd)
                                        {
                                            tmpOut = pOutArr + (tmpOutEnd - tmpOut);
                                        }
                                    }
                                }
                            }
                        }
                    }
                    #endregion
                }
                else if (inArray.IsVector)
                {
                    #region Vector
                    ////////////////////////////   VECTOR   ///////////////////////
                    unsafe
                    {
                        fixed(int *leadDimStart = idxOffset[leadDim])
                        {
                            fixed(byte *pOutArr = retByteArr)
                            {
                                fixed(double *pInArr = inArray.m_data)
                                {
                                    byte *  tmpOut     = pOutArr;
                                    double *tmpIn      = pInArr + idxOffset[((leadDim + 1) % 2), 0];
                                    int *   leadDimIdx = leadDimStart;
                                    int *   leadDimEnd = leadDimStart + leadDimLen;

                                    // start at first element
                                    while (leadDimIdx < leadDimEnd)
                                    {
                                        *tmpOut++ = operation(*(tmpIn + *leadDimIdx++));
                                    }
                                }
                            }
                        }
                    }
                    #endregion
                }
                else
                {
                    /////////////////////////////   ARBITRARY DIMENSIONS //////////
                    #region arbitrary size
                    unsafe {
                        int[] curPosition = new int[inArray.Dimensions.NumberOfDimensions];
                        fixed(int *leadDimStart = idxOffset[leadDim])
                        {
                            fixed(byte *pOutArr = retByteArr)
                            {
                                fixed(double *pInArr = inArray.m_data)
                                {
                                    byte *tmpOut    = pOutArr;
                                    byte *tmpOutEnd = tmpOut + retByteArr.Length;
                                    // init lesezeiger: add alle Dimensionen mit 0 (außer leadDim)
                                    double *tmpIn = pInArr + inArray.getBaseIndex(0, 0);

                                    tmpIn -= idxOffset[leadDim, 0];
                                    int *leadDimIdx = leadDimStart;
                                    int *leadDimEnd = leadDimStart + leadDimLen;
                                    int  dimLen = curPosition.Length;
                                    int  d, curD;

                                    // start at first element
                                    while (tmpOut < tmpOutEnd)
                                    {
                                        leadDimIdx = leadDimStart;
                                        while (leadDimIdx < leadDimEnd)
                                        {
                                            *tmpOut = operation(*(tmpIn + *leadDimIdx++));
                                            tmpOut += incOut;
                                        }
                                        if (tmpOut > tmpOutEnd)
                                        {
                                            tmpOut = pOutArr + (tmpOutEnd - tmpOut);
                                        }

                                        // increment higher dimensions
                                        d = 1;
                                        while (d < dimLen)
                                        {
                                            curD   = (d + leadDim) % dimLen;
                                            tmpIn -= idxOffset[curD, curPosition[curD]];
                                            curPosition[curD]++;
                                            if (curPosition[curD] < idxOffset[curD].Length)
                                            {
                                                tmpIn += idxOffset[curD, curPosition[curD]];
                                                break;
                                            }
                                            curPosition[curD] = 0;
                                            tmpIn            += idxOffset[curD, 0];
                                            d++;
                                        }
                                    }
                                }
                            }
                        }
                    }
                    #endregion
                }
                // ==============================================================
                #endregion
            }
            else
            {
                // physical -> pointer arithmetic
                #region physical storage
                unsafe
                {
                    fixed(byte *pOutArr = retByteArr)
                    {
                        fixed(double *pInArr = inArray.m_data)
                        {
                            byte *  lastElement = pOutArr + retByteArr.Length;
                            byte *  tmpOut      = pOutArr;
                            double *tmpIn       = pInArr;

                            while (tmpOut < lastElement)
                            {
                                *tmpOut++ = operation(*tmpIn++);
                            }
                        }
                    }
                }
                #endregion
            }
            return(new ILLogicalArray(retByteArr, inDim.ToIntArray()));
        }
コード例 #2
0
ファイル: ILMath.cs プロジェクト: wdxa/ILNumerics
		/// <summary>
		/// Applys the function (delegate) given to all elements of the storage
		/// </summary>
		/// <param name="inArray">storage array to be apply the function to</param>
		/// <param name="operation">operation to apply to the elements of inArray. This
		/// acts like a function pointer.</param>
		/// <returns>new ILArray<double> with result</returns>
		/// <remarks> the values of inArray will not be altered.</remarks>
		private static ILLogicalArray LogicalUnaryDoubleOperator(ILArray<double> inArray, ILApplyLogical_Double operation) {
			ILDimension inDim = inArray.Dimensions;
            byte[] retByteArr;
			// build ILDimension
			int newLength = inDim.NumberOfElements;
            retByteArr = new byte[newLength];
			int leadDim = 0;
			int leadDimLen = inDim[0];
			if (inArray.IsReference) {
				#region Reference storage
				// walk along the longest dimension (for performance reasons)
				for (int i = 1; i < inDim.NumberOfDimensions; i++) {
					if (leadDimLen < inDim[i]) {
						leadDimLen = inDim[i];
						leadDim = i;
					}
				}
				ILIndexOffset idxOffset = inArray.m_indexOffset;
				int incOut = inDim.SequentialIndexDistance(leadDim);
				// ========================  REFERENCE double Storage ===========
				if (inArray.IsMatrix) {
					#region Matrix
					////////////////////////////   MATRIX   ////////////////////
					int secDim = (leadDim + 1) % 2;
					unsafe {
						fixed (int* leadDimStart = idxOffset[leadDim],
								secDimStart = idxOffset[secDim]) {
                            fixed (byte* pOutArr = retByteArr) {
								fixed (double* pInArr = inArray.m_data) {
                                    byte* tmpOut = pOutArr;
									double* tmpIn = pInArr;
                                    byte* tmpOutEnd = pOutArr + inDim.NumberOfElements - 1;
									int* secDimEnd = secDimStart + idxOffset[secDim].Length;
									int* secDimIdx = secDimStart;
									int* leadDimIdx = leadDimStart;
									int* leadDimEnd = leadDimStart + idxOffset[secDim].Length; ;
									while (secDimIdx < secDimEnd) {
										tmpIn = pInArr + *secDimIdx++;
										leadDimIdx = leadDimStart;
										while (leadDimIdx < leadDimEnd) {
											*tmpOut = operation(*(tmpIn + *leadDimIdx++));
											tmpOut += incOut;
										}
										if (tmpOut > tmpOutEnd)
											tmpOut = pOutArr + (tmpOutEnd - tmpOut);
									}
								}
							}
						}
					}
					#endregion
				} else if (inArray.IsVector) {
					#region Vector
					////////////////////////////   VECTOR   ///////////////////////
					unsafe {
						fixed (int* leadDimStart = idxOffset[leadDim]) {
                            fixed (byte* pOutArr = retByteArr) {
								fixed (double* pInArr = inArray.m_data) {
                                    byte* tmpOut = pOutArr;
									double* tmpIn = pInArr + idxOffset[((leadDim + 1) % 2), 0];
									int* leadDimIdx = leadDimStart;
									int* leadDimEnd = leadDimStart + leadDimLen;
									// start at first element
									while (leadDimIdx < leadDimEnd)
										*tmpOut++ = operation(*(tmpIn + *leadDimIdx++));
								}
							}
						}
					}
					#endregion
				} else {
					/////////////////////////////   ARBITRARY DIMENSIONS //////////
					#region arbitrary size
					unsafe {
						int[] curPosition = new int[inArray.Dimensions.NumberOfDimensions];
						fixed (int* leadDimStart = idxOffset[leadDim]) {
                            fixed (byte* pOutArr = retByteArr) {
								fixed (double* pInArr = inArray.m_data) {
                                    byte* tmpOut = pOutArr;
                                    byte* tmpOutEnd = tmpOut + retByteArr.Length;
									// init lesezeiger: add alle Dimensionen mit 0 (außer leadDim)
									double* tmpIn = pInArr + inArray.getBaseIndex(0, 0);
									tmpIn -= idxOffset[leadDim, 0];
									int* leadDimIdx = leadDimStart;
									int* leadDimEnd = leadDimStart + leadDimLen;
									int dimLen = curPosition.Length;
									int d, curD;
									// start at first element
									while (tmpOut < tmpOutEnd) {
										leadDimIdx = leadDimStart;
										while (leadDimIdx < leadDimEnd) {
											*tmpOut = operation(*(tmpIn + *leadDimIdx++));
											tmpOut += incOut;
										}
										if (tmpOut > tmpOutEnd)
											tmpOut = pOutArr + (tmpOutEnd - tmpOut);

										// increment higher dimensions 
										d = 1;
										while (d < dimLen) {
											curD = (d + leadDim) % dimLen;
											tmpIn -= idxOffset[curD, curPosition[curD]];
											curPosition[curD]++;
											if (curPosition[curD] < idxOffset[curD].Length) {
												tmpIn += idxOffset[curD, curPosition[curD]];
												break;
											}
											curPosition[curD] = 0;
											tmpIn += idxOffset[curD, 0];
											d++;
										}
									}
								}
							}
						}
					}
					#endregion
				}
				// ==============================================================
				#endregion
			} else {
				// physical -> pointer arithmetic
				#region physical storage
				unsafe {
                    fixed (byte* pOutArr = retByteArr) {
						fixed (double* pInArr = inArray.m_data) {
                            byte* lastElement = pOutArr + retByteArr.Length;
                            byte* tmpOut = pOutArr;
							double* tmpIn = pInArr;
							while (tmpOut < lastElement)
								*tmpOut++ = operation(*tmpIn++);
						}
					}
				}
				#endregion
			}
			return new ILLogicalArray(retByteArr, inDim.ToIntArray());
		}