poj-1362

来源:互联网 发布:专业软件开发学院 编辑:程序博客网 时间:2024/04/30 14:50
//356K  0MS G++#include <cstdio>#include <cstring>const int MAX = 40;long long rankWeight[MAX];void init() {    long long begin = 2;    for (int i = 0; i < MAX; i++) {        rankWeight[i] = begin - 1;        // printf("%lld ", rankWeight[i]);        begin <<= 1;    }    // printf("\n");}http://write.blog.csdn.net/postedit/39203945int binarySearch(int val) {    // printf("binarySearch %d\n", val);    int begin = 0;    int end = MAX-1;    while(1) {        if (begin > end) {            break;        }        int mid = (begin + end)/2;        if (rankWeight[mid] == val) {            // printf("%d found!\n", val);            return mid;        } else if (rankWeight[mid] > val) {            end = mid - 1;        } else if (rankWeight[mid] < val) {            begin = mid + 1;        }    }    // printf("%d not found!\n", val);    return -1;}int res[30];int resPos;int caseNum;long long getMaxLessEqualThan(int demicalVal, int & weightRank) {    long long res = 0;    for (int i = 0; i <MAX; i++) {        if (rankWeight[i] > demicalVal) {            res = rankWeight[i-1];            weightRank = i-1;            break;        }    }    return res;}void getSkewBinary(int demicalVal) {    if (demicalVal == 0) {        printf("0 []\n");        return;    }    int curDemicalVal = demicalVal;    while(1) {        int CurValWeightRank = binarySearch(curDemicalVal);        if (CurValWeightRank >= 0) {            res[resPos++] = CurValWeightRank;            break;        } else {            if (curDemicalVal%2==0) {                int halfVal = curDemicalVal/2;                if (halfVal%2 == 1) {                    int HalfCurValWeightRank = binarySearch(halfVal);                    if (HalfCurValWeightRank >= 0) {                        res[resPos++] = HalfCurValWeightRank;                        res[resPos++] = HalfCurValWeightRank;                        break;                    }                }            }            int weightRank = -1;            int MaxLessEqual = getMaxLessEqualThan(curDemicalVal, weightRank);            if (MaxLessEqual == 0 || weightRank == -1) {                break;            } else {                res[resPos++] = weightRank;                curDemicalVal -= MaxLessEqual;            }        }    }    long long checkVal = 0;    printf("%d [", demicalVal);    for (int i = resPos-1; i >= 0; i--) {        checkVal += rankWeight[res[i]];        if (i >0) {            printf("%d,", res[i]);        } else if (i == 0) {            printf("%d", res[i]);        }    }    printf("]\n");    // printf("%lld\n", checkVal);}int main() {    init();    scanf("%d", &caseNum);    for (int i = 1; i <= caseNum; i++) {        int demicalVal;        memset(res, 0xff, sizeof(res));        resPos = 0;        scanf("%d", &demicalVal);        getSkewBinary(demicalVal);    }}

题意比较难懂,不过懂了以后也算个小水题吧。

题意是给了一堆的进制权,i从0开始,依次是2的i+1次方减一(1, 3, 7 , 15),对于某个十进制数,都要用这些进制位将其表示出来,依照从进制权值从小到大的顺序:

另外有一点就是不能有两个相同的进制权位相邻,除非是最开始的两位。

比如:

对于 15, 【0 3 3】 也等于 15(0的权值 1 + 3的权值7 + 3的权值7 = 15),但是因为3 3不是最后两位,所以不行,

同时,因为权值都是奇数,所以不存在一个偶数有两种表示的方式 (比如 [k,k] 或者 [m])

这样策略就简单了:

对于一个十进制数S ,先看看其是否就是一个权值,如果是,那么直接将权值对应的位输出即可,

否则,再看其是是否为偶数,如果是偶数,在看S/2是否是一个权值V,如果是,那么直接输出[V,V],

否则,就找到最大的小于S的权值,将其对应位加入到结果数组中,并且,S 减去此权值,继续操作,

知道S == 0,整个过程结束.

0 0
原创粉丝点击