public WaveletD4Transform(int dataDim)
        {
            dim = HaarTransform.RoundDimension(dataDim);
            InitializeConstants();
            D4 = WaveTransforms.App.ScriptApp.New.NumberTable(dim, dim);

            // Algorithm adapated from: http://www.bearcave.com/misl/misl_tech/wavelets/daubechies/daub.java
            for (int row = 0; row < dim; row++)
            {
                double[] v = (D4.Matrix as double[][])[row];
                Array.Clear(v, 0, v.Length);
                v[row] = 1.0;
                for (int n = v.Length; n >= 4; n >>= 1)
                {
                    TransformD4(v, n);
                }
            }

            int interval = dim / 16;

            for (int k = 0; k < dim; k++)
            {
                D4.RowSpecList[k].Type = D4.ColumnSpecList[k].Group = (short)(k / interval);
            }

            List <int> rows = new List <int>();

            for (int row = 0; row < dataDim; row++)
            {
                rows.Add(row);
            }
            D4 = D4.SelectRows(rows);
        }
Beispiel #2
0
        public HaarTransform(int dataDim)
        {
            dim  = RoundDimension(dataDim);
            haar = WaveTransforms.App.ScriptApp.New.NumberTable(dim, dim);


            // Algorithm adapated from: http://www.cs.ucf.edu/~mali/haar/.
            double sqrt2 = 1 / Math.Sqrt(2.0);

            double[] vp = new double[dim];
            for (int row = 0; row < dim; row++)
            {
                double[] v = (haar.Matrix as double[][])[row];
                Array.Clear(v, 0, v.Length);
                v[row] = 1.0;
                Array.Clear(vp, 0, vp.Length);

                int w = dim;
                while (w > 1)
                {
                    w /= 2;
                    for (int i = 0; i < w; i++)
                    {
                        vp[i]     = (v[2 * i] + v[2 * i + 1]) * sqrt2;
                        vp[i + w] = (v[2 * i] - v[2 * i + 1]) * sqrt2;
                    }
                    Array.Copy(vp, v, 2 * w);
                }
            }

            int interval = dim / 16;

            for (int k = 0; k < dim; k++)
            {
                haar.RowSpecList[k].Type = haar.ColumnSpecList[k].Group = (short)(k / interval);
            }

            List <int> rows = new List <int>();

            for (int row = 0; row < dataDim; row++)
            {
                rows.Add(row);
            }
            haar = haar.SelectRows(rows);
        }
Beispiel #3
0
        public INumberTable Filter(INumberTable inTable, double lowFreq, double highFreq)
        {
            INumberTable freqTable = Transform(inTable);

            //
            // Since the frequency vectors are half vector (the other half are mirred and not stored)
            // we need to duplicate the vector except the first and, in case n is even, the n/2 th element.
            // Notice that the Fourier matrixes have the same mirred structure.
            //
            for (int row = 0; row < freqTable.Rows; row++)
            {
                for (int col = 0; col < freqTable.Columns; col++)
                {
                    int c = col % tDim; // c is the index within the repeat interval.
                    if (c == 0)
                    {
                        continue;
                    }
                    if ((tDim % 2 == 0) && (c == tDim / 2))
                    {
                        // In case tDim is even, the n/2-th element is at the centre of the symmetry
                        // and must not be duplciated.
                        continue;
                    }

                    freqTable.Matrix[row][col] *= 2;
                }
            }

            // Calculate the filter indexes to pick up bases vectors
            // with frequency (stored as column group)falling between give range.
            int                 lFreq      = (int)(lowFreq * (tDim / 2 + 1));
            int                 hFreq      = (int)(highFreq * (tDim / 2 + 1));
            List <int>          filterReal = new List <int>();
            List <int>          filterImg  = new List <int>();
            List <int>          filterFreq = new List <int>();
            IList <IColumnSpec> mrSpecList = matrixReal.ColumnSpecList;

            foreach (int idx in selectReal)
            {
                int freq = mrSpecList[idx].Group;
                if ((lFreq <= freq) && (freq <= hFreq))
                {
                    filterReal.Add(idx);
                    filterFreq.Add(idx);
                }
            }
            IList <IColumnSpec> miSpecList = matrixImg.ColumnSpecList;

            foreach (int idx in selectImg)
            {
                int freq = miSpecList[idx].Group;
                if ((lFreq <= freq) && (freq <= hFreq))
                {
                    filterImg.Add(idx);
                    filterFreq.Add(tDim / 2 + idx);
                }
            }

            int repeats = freqTable.Columns / tDim;

            if (repeats > 1)
            {
                // the transformation has been repeated. We need to add the repeated coefficient here.
                for (int r = 1; r < repeats; r++)
                {
                    for (int n = 0; n < tDim; n++)
                    {
                        filterFreq.Add(r * tDim + filterFreq[n]);
                    }
                }
            }

            freqTable = freqTable.SelectColumns(filterFreq);
            INumberTable revMatrix = matrixReal.SelectRows(filterReal).Append(matrixImg.SelectRows(filterImg));
            INumberTable outTable  = MatrixProduct(freqTable, revMatrix);

            IList <IColumnSpec> oSpecList = outTable.ColumnSpecList;
            IList <IColumnSpec> iSpecList = inTable.ColumnSpecList;

            for (int col = 0; col < outTable.Columns; col++)
            {
                if (col < inTable.Columns)
                {
                    oSpecList[col].CopyFrom(iSpecList[col]);
                }
            }
            return(outTable);
        }
Beispiel #4
0
        public WalshTransform(int dataDim)
        {
            dim   = HaarTransform.RoundDimension(dataDim);
            walsh = WaveTransforms.App.ScriptApp.New.NumberTable(dim, dim);

            //
            // The Walsh matrix differs from Hadamard in ordering of the base vectors:
            // the former uses the sequency order (bit-reversal or Gray code permutation)
            // while the latter uses nature order resulted
            // from recursive calculation.
            //
            // The following code is adapted from http://www.musicdsp.org/showone.php?id=18.
            int log2 = Log2(dim);

            for (int row = 0; row < dim; row++)
            {
                double[] v = (walsh.Matrix as double[][])[row];
                v[row] = 1.0;

                for (int i = 0; i < log2; i++)
                {
                    int i2 = (1 << i);
                    for (int j = 0; j < (1 << log2); j += 2 * i2)
                    {
                        for (int k = 0; k < i2; k++)
                        {
                            int    jk = j + k;
                            double a  = v[jk] + v[jk + i2];
                            v[jk + i2] = v[jk] - v[jk + i2];
                            v[jk]      = a;
                        }
                    }
                }
            }

            //
            // perform the bit-reserve and gray code re-ordering.
            //
            int[] order    = new int[dim];
            int[] grayCode = GrayOrder(log2);
            for (int i = 0; i < dim; i++)
            {
                order[i] = ReverseOrder(log2, grayCode[i]);
            }

            // Permutate the rows.
            double[][] newM = new double[dim][];
            double[][] M    = walsh.Matrix as double[][];
            for (int row = 0; row < dim; row++)
            {
                newM[row] = M[order[row]];
            }
            for (int row = 0; row < dim; row++)
            {
                M[row] = newM[row];
            }

            int interval = dim / 16;

            for (int k = 0; k < dim; k++)
            {
                walsh.RowSpecList[k].Type = walsh.ColumnSpecList[k].Group = (short)(k / interval);
            }

            // Remove the redudant rows.
            List <int> rows = new List <int>();

            for (int row = 0; row < dataDim; row++)
            {
                rows.Add(row);
            }
            walsh = walsh.SelectRows(rows);

            // Normalize the matrix.
            double normFactor = Math.Pow(2, -log2 / 2.0);

            for (int row = 0; row < walsh.Rows; row++)
            {
                for (int col = 0; col < walsh.Columns; col++)
                {
                    walsh.Matrix[row][col] *= normFactor;
                }
            }
        }