zoukankan      html  css  js  c++  java
  • Poj 1147 Binary codes bwt压缩算法(很巧妙的一种算法)

    题目连接:http://poj.org/problem?id=1147

    题目描述:就是求解bwt压缩算法的逆过程。

    一个长度为N的01序列,会有N个不同的轮换(当然,字符相同,其中也可能会有相同的),将这N个不同轮换按字典序排序,取排序后的每个轮换的最后一排,组成一个序列。题中给出压缩后的序列,求原始序列,输出的是字典序最小的那个序列

    解法:整个解法还挺巧妙的,具体百度上也有解释,简单的根据体重给出的例子说一下:

    0 0 0 1 1
    0 0 1 1 0
    0 1 1 0 0
    1 0 0 0 1
    1 1 0 0 0

    给出的序列中0和1的个数肯定是和原始序列一样的,即由最后一列的数据10010可知原始序列中有2个0和3个1,所以将最后一列(10010)进行排序,即可得到第一列的数据(00011)。上述5*5数组中,将最后一列的数据移到第一列,得一下序列

     

    1

    0

    0

    0

    1

    0

    0

    0

    1

    1

    0

    0

    1

    1

    0

    1

    1

    0

    0

    0

    0

    1

    1

    0

    0

    (2)

    而上述五个轮换中的第一列与第二列是可以知道的,如果要将上述五个轮换按字典序排序后变成(1),则需要进行相应转换,可知如果开头都是1或者都是0则先后顺序仍然不变,只需把①②③④⑤变成②③⑤①④即可,这个时候将(2)中的第二列(00011)与第一列(10010)同时变化,即可得到(1)中的第二列(00101),以此类推,现在(1)中的第一、二列都已经知道,按照同样的推演方式即可得到(1)中,即原始序列中的所有列的元素,即可得到原始序列。

     1 #include<iostream>
     2 #include<cstdio>
     3 #include<cmath>
     4 #include<cstring>
     5 #include<algorithm>
     6 #define N 3010
     7 using namespace std;
     8 bool last[N], first[N], goal[N], temp[N];
     9 int t[N];
    10 int main(){
    11     int n, i, j, k, l;
    12     while(~scanf("%d",&n)){
    13         k=0;
    14         for(i=0;i<n;i++){
    15             scanf("%d",&last[i]);
    16             if(last[i]==0){
    17                 first[k]=last[i];
    18                 t[i] = k;
    19                 k++;
    20             }
    21         }
    22         for(i=0;i<n;i++){
    23             if(last[i]==1){
    24                 first[k]=last[i];
    25                 t[i]=k;
    26                 k++;
    27             }
    28         }
    29         goal[0]=first[0];
    30         for(j=1;j<n;j++){
    31             if(j%2){
    32                 for(i=0;i<n;i++){
    33                     temp[t[i]]=first[i];
    34                 }
    35                 goal[j] = temp[0];
    36             }
    37             else{
    38                 for(i=0;i<n;i++){
    39                     first[t[i]]=temp[i];
    40                 }
    41                 goal[j] = first[0];
    42             }
    43         }
    44         for(i=0;i<n-1;i++){
    45             printf("%d ",goal[i]);
    46         }
    47         printf("%d\n",goal[i]);
    48     }
    49     return 0;
    50 }
  • 相关阅读:
    leetcode 350. Intersection of Two Arrays II
    leetcode 278. First Bad Version
    leetcode 34. Find First and Last Position of Element in Sorted Array
    leetcode 54. Spiral Matrix
    leetcode 59. Spiral Matrix II
    leetcode 44. Wildcard Matching
    leetcode 10. Regular Expression Matching(正则表达式匹配)
    leetcode 174. Dungeon Game (地下城游戏)
    leetcode 36. Valid Sudoku
    Angular Elements
  • 原文地址:https://www.cnblogs.com/celia01/p/2435548.html
Copyright © 2011-2022 走看看