CSU 1977: Bit-reversal Permutation

原创 2017年08月13日 09:25:47

CSU 1977: Bit-reversal Permutation

Description

A fast Fourier transform (FFT) algorithm computes the discrete Fourier transform (DFT) of a sequence, or its inverse (IFFT). Fourier analysis converts a signal from its original domain (often time or space) to a representation in the frequency domain and vice versa. An FFT rapidly computes such transformations by factorizing the DFT matrix into a product of sparse (mostly zero) factors. As a result, it manages to reduce the complexity of computing the DFT from O(n2), which arises if one simply applies the definition of DFT, to O(nlogn), where n is the data size.

——From Wikipedia

During this summer holiday, csuxushu feels so bored to learn FFT. Because FFT is a complicated algorithm, he need to apply a bit-reversal permutation to a sequence first before DFT which is a part of FFT.

In applied mathematics, a bit-reversal permutation is a permutation of a sequence of n items, where n = 2^k is a power of two. It is defined by indexing the elements of the sequence by the numbers from 0 to n ? 1 and then reversing the binary representations of each of these numbers (padded so that each of these binary numbers has length exactly k). Each item is then mapped to the new position given by this reversed value.

Because all fellows in CSU(California State University ) can apply FFT, NTT or even FWT, it is a shame that he even doesn’t know how to take the first step. As one of the best computer programmer in CSU, can you help him?

You may think this problem is too hard to solve. In fact, it is a piece of cake to you. Remember to see the hint :-)

Input

The first line of the input gives the number of test cases T(T≤10); T test cases follow.Each test case contains a number sequence.
In each case, the first line is a number N(1≤N≤10^5), the number of elements in the following sequence.The second line is the sequence.Its length may not be exactly a power of two, so you can append some zeros to make it the minimal power of two larger than or equal to N.

Output

For each test case, output the sequence from input in bit-reversal order.

Sample Input

1
6
21 58 96 12 45 65

Sample Output

21 45 96 0 58 65 12 0

Hint

Bit-reverse Order
中文提示:可以看到,我们最终处理的系数从左至右的编号的二进制形式分别为000,100,010,110,001,101,011,111,若将其二进制反序,可得000,001,010,011,100,101,110,111,这些反序的二进制编码是从小到大排列的。也就是说,我们可以按照每个下标的二进制编码来确定处理系数的顺序。这种方法就称为位逆序置换(Bit-reversal permutation)

Source

2017年8月月赛

Author

徐戍

题目大意

模拟实现DFT的第一步:将数组元素重新按位逆序排列。

输入:a0,a1,a2,a3,a4,a5,a6,a7 二进制下标 000,001,010,011,100,101,110,111

输出:a0,a4,a2,a6,a1,a5,a3,a7 二进制下标 000,100,010,110,001,101,011,111

思路

如果我们能够将输出的二进制下标按顺序生成出来,那么只要依次输出下标对应的元素即可,因此我们要找出位逆序排列的规律。

其实位顺序排列和位逆序排列是同样的一串字符从不同的方向来看罢了,完全可以按顺序生成二进制后反向转换成十进制即可。

#include <iostream>
#include <cstdio>
#include <string>
#include <cstring>
using namespace std;
int t,n;
int a[100005];
int b[100005];
int btc[100005];
int len;
int reserval(int x)
{
    int ans = 0;
    for(int i = len-1 ; i >= 0 ; i--)
    {
        if((x & (1 << len-1-i)) == 0)
            continue;
        ans = ans | (1 << i);
    }
    return ans;
}
int main()
{
    int num = 1;
    for(int i = 2 ; i <= 100000 ; i *= 2)
        b[i] = num++;
    num = 1;
    for(int i = 1 ; i <= 100000 ; i++)
        if(!b[i]) btc[i] = num;
        else btc[i] = num++;
    scanf("%d",&t);
    while(t--)
    {
        scanf("%d",&n);
        for(int i = 0 ; i < n ; i++)
            scanf("%d",&a[i]);
        len = btc[n];
        int nn  = 1 << btc[n];
        for(int i = 0 ; i < nn ; i++)
            printf("%d%c",reserval(i) >= n ? 0:a[reserval(i)]," \n"[i == nn-1]);
    }
    return 0;
}

位运算交换 (FFT模板节选)

// 原地快速bit reversal
for(i = 0, j = 0; i < n; i++) {
    if(j > i) swap(a[i], a[j]);
    int k = n;
    while(j & (k >>= 1)) j &= ~k;
    j |= k;
}
版权声明:本文为博主原创文章,未经博主允许不得转载。

Bit Reversal and Permutation

next>>  tables>> Bit Reversal and Permutation for Radix 2 In order to use the FFT sche...
  • bbvs1
  • bbvs1
  • 2016年12月23日 16:54
  • 412

1977: Bit-reversal Permutation(递归)

1977: Bit-reversal Permutation Submit Page Summary Time Limit: 1 Sec Memory Limit: 128 ...
  • u013306830
  • u013306830
  • 2017年08月12日 13:01
  • 37

1977:Bit-reversal Permutation

Description A fast Fourier transform (FFT) algorithm computes the discrete Fourier transform (DFT) ...
  • Eira_H
  • Eira_H
  • 2017年08月12日 17:14
  • 149

Bit-reversal permutation

转自维基百科: In applied mathematics, a bit-reversal permutation is a permutation of a sequence of n item...
  • dumeichen
  • dumeichen
  • 2015年09月29日 15:14
  • 182

CSU1977: Bit-reversal Permutation

CSU1977: Bit-reversal PermutationDescriptionA fast Fourier transform (FFT) algorithm computes the di...
  • xiyue_jiang
  • xiyue_jiang
  • 2017年08月13日 08:59
  • 60

CSU wifi免帐号自动登陆器

原理很简单,采用数据包提交的方式提交到服务端。 一下是源代码:(Ubuntu13.04 64位 Linux) #include #include #include #include #...
  • dl6210
  • dl6210
  • 2013年06月15日 14:20
  • 960

【C语言训练】计算1977!*

1130: 【C语言训练】计算1977!* Time Limit: 1 Sec  Memory Limit: 128 MB Submit: 7  Solved: 4 [Submit][Statu...
  • baidu_23955875
  • baidu_23955875
  • 2015年03月02日 21:16
  • 766

1977的阶乘计算

#include int mult(int num[],int len,int n) { long i,rem=0; for(i=0;i
  • baidu_23955875
  • baidu_23955875
  • 2014年12月10日 17:25
  • 712

csu/dsu与dte/dce的概念区别

csu/dsu与dte/dce的概念区别   CSU(通道服务单元):把终端用户和本地数字电话环路相连的数字接口设备。通常它和DSU统称为CSU/DSU  DSU(数据业务单元):指的是用于数字传...
  • wjx515628
  • wjx515628
  • 2013年07月08日 13:28
  • 2978

bzoj 1977 (浅谈如何hack掉hzwer学长)(严格次小生成树)(LCA+kruskal)

传送门 题解:(**以下内容出自代码有错但是过了bzoj评测的hwzer学长**)先求出最小生成树,要严格次小。枚举每一条非树边找俩顶点树链上的最大边(如果最大边相同与非树边边权相同则找次大边)然后...
  • KGV093
  • KGV093
  • 2017年10月15日 21:50
  • 153
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:CSU 1977: Bit-reversal Permutation
举报原因:
原因补充:

(最多只允许输入30个字)