Exemple #1
0
        private PermutationNetwork CreateBorderSorter(int borderBitLength, int intraBlockSortQuality)
        {
            PermutationNetwork pn = new PermutationNetwork(1 << (borderBitLength + 1));

            int borderSize = 1 << borderBitLength;
            int listCount  = (1 << (intraBlockSortQuality + 1));
            int listSize   = borderSize / listCount;

            pn.AppendGate(PermutationGateFactory.CreateUnshuffleGate(borderSize, listCount), 0);
            pn.AppendGate(PermutationGateFactory.CreateUnshuffleGate(borderSize, listCount), borderSize);

            // merge the corresponding lists
            for (int i = 0; i < listCount; i++)
            {
                int[] wires = new int[listSize * 2];
                for (int j = 0; i < listSize; i++)
                {
                    wires[j]            = i * listSize + j;
                    wires[j + listSize] = wires[j] + borderSize;
                }

                pn.AppendNetwork(SortingNetworkFactory.CreateBitonicMerge(listSize * 2, false), wires);
            }

            // shuffle the lists back into the blocks
            pn.AppendGate(PermutationGateFactory.CreateShuffleGate(borderSize, listCount), 0);
            pn.AppendGate(PermutationGateFactory.CreateShuffleGate(borderSize, listCount), borderSize);

            return(pn);
        }
Exemple #2
0
        // Lemma 4.1
        private PermutationNetwork CreateBlockCorrectionNetwork(int blockBitLength, int unsortedness)
        {
            PermutationNetwork pn = new PermutationNetwork(1 << blockBitLength);

            SortedSet <int> ySet = new SortedSet <int>(CalculationCache.generateY(blockBitLength));

            Debug.Assert(ySet.Count <= 1 << unsortedness);
            // augment Y with arbitrary elements
            int ySize     = 1 << (unsortedness + 1);
            int blockSize = 1 << blockBitLength;

            Random rand = new Random(0);

            while (ySet.Count < ySize)
            {
                ySet.Add(rand.Next(blockSize));
            }

            // here our implementation differs from the paper.  The paper first to extract Y then order the X by the permutation pi.
            // Instead, we will order all of the inputs by the permutation pi, then map Y using the permutation pi and move X to the top of the block
            // and Y to the bottom so that we can unshuffle X and add Y.

            int[] pi = CalculationCache.generatePi(blockBitLength);

            pn.AppendGate(new PermutationGate(pi), 0);

            int[] mappedY = new int[ySize];
            int   i       = 0;

            foreach (var yElem in ySet)
            {
                mappedY[i++] = pi[yElem];
            }

            pn.AppendGate(PermutationGateFactory.CreateSplitGate(blockSize, mappedY, false), 0);

            // we now want to unshuffle X into 2^(l+1) groups and add one element of Y to each group

            pn.AppendGate(PermutationGateFactory.CreateUnshuffleGate(blockSize - ySize, ySize), 0);

            pn.AppendGate(PermutationGateFactory.CreateMultiGroupInserterGate(blockSize, (blockSize / ySize) - 1, ySize), 0);

            var treeInsertion = SortingNetworkFactory.CreateBinaryTreeInsertion(blockSize / ySize);

            // use binary tree insertion to insert the elemnt we just added to each group
            for (int j = 0; j < ySize; j++)
            {
                pn.AppendNetwork(treeInsertion.Clone() as PermutationNetwork, j * blockSize / ySize);
            }

            // now shuffle all of the lists back together
            pn.AppendGate(PermutationGateFactory.CreateShuffleGate(blockSize, ySize), 0);

            return(pn);
        }
Exemple #3
0
        public static PermutationNetwork CreateBitonicSplit(int wireCount, bool invertOrder)
        {
            Debug.Assert(SortingNetwork.isPowerOfTwo((uint)wireCount));

            PermutationNetwork pn = new PermutationNetwork(wireCount);

            for (int i = 0; i < wireCount / 2; i++)
            {
                pn.AppendGate(new ComputationGate(ComputationGateType.COMPARE_AND_SWAP), new int[] { i, i + wireCount / 2 });
                if (invertOrder)
                {
                    pn.AppendGate(PermutationGateFactory.CreateSwapGate(), new int[] { i, i + wireCount / 2 });
                }
            }

            return(pn);
        }
Exemple #4
0
        // Lemma 4.3
        private PermutationNetwork CreateFinalSorter(int blockBitLength)
        {
            PermutationNetwork pn = new PermutationNetwork(1 << K);

            int blockSize  = 1 << blockBitLength;
            int blockCount = 1 << (K - blockBitLength);

            // sort each block, alternate orders for bitonic merge coming up
            var bitonicSort = SortingNetworkFactory.CreateBitonicSort(blockSize, false);

            for (int i = 0; i < blockCount; i++)
            {
                pn.AppendNetwork(bitonicSort, i * blockSize);
                if (i % 2 == 1)
                {
                    pn.AppendGate(PermutationGateFactory.CreateInvertGate(blockSize), i * blockSize);
                }
            }

            PermutationNetwork twoBlockMerge = SortingNetworkFactory.CreateBitonicMerge(blockSize * 2, false);

            // merge each block with the one next to it.  alternate ordern for bitonic merge coming up

            var bitonicMerge = SortingNetworkFactory.CreateBitonicMerge(blockSize * 2, false);

            for (int i = 0; i < blockCount; i += 2)
            {
                pn.AppendNetwork(bitonicMerge.Clone() as PermutationNetwork, i * blockSize);
                if ((i / 2) % 2 == 1)
                {
                    pn.AppendGate(PermutationGateFactory.CreateInvertGate(2 * blockSize), i * blockSize);
                }
            }

            // do another round of merges, this time offset by 1
            for (int i = 1; i < blockCount; i += 2)
            {
                pn.AppendNetwork(bitonicMerge.Clone() as PermutationNetwork, i * blockSize);
            }

            // the last block will be inverted, so uninvert it
            pn.AppendGate(PermutationGateFactory.CreateInvertGate(blockSize), (blockCount - 1) * blockSize);

            return(pn);
        }