繁体   English   中英

二进制到十进制基本移位

[英]binary to decimal base shift

我需要一种算法,可以将任意大小的无符号整数(以二进制格式存储)转换为十进制数。 即使其易于阅读;)
我目前使用(也许很显然)有些天真的方法来连续计算模数和除以十的余数。
不幸的是,速度有些... la脚。

例如,我计算了2000 ^ 4000(使用我的bignum库),这大约需要1.5秒(请不要燃烧,请xD)。 但是,包括必要的基本转换的打印大约需要15分钟,这很烦人。

我已经测试了bc,而这两个过程都不​​到一秒钟。
它是如何做到的? (不是与ffts相乘的东西,仅与基本转换无关)

我目前使用(也许很显然)有些天真的方法来连续计算模数和除以十的余数。
然后,您应该具有O(n^2)复杂度,该复杂度应该比15分钟好得多。

虽然,值得一提的是如何精确地除以10

  1. 确保您不是应用长整数的通用除法,而是应用标准的简单的将长数除法的算法。
  2. 确保您重复使用内存。 分配10Kb块10000次肯定会影响您的性能。

编辑
如何一次性将长二进制数除以10并得到结果和提示。 没有额外的内存。
简单伪代码( a[0]是最高位)

int r = 0;
for (int i = 0; i < n; ++i) {
    r = r * 2 + a[i];
    a[i] = r / 10;
    r = r % 10;
}

让我们举个例子,数字100111011 = 315

步骤0: r = 1, a[0] = 0
步骤1: r = 2, a[1] = 0
步骤2: r = 4, a[2] = 0
步骤3: r = 9, a[3] = 0
步骤4: r = 9, a[4] = 1
步骤5: r = 9, a[5] = 1
步骤6: r = 8, a[6] = 1
步骤7: r = 7, a[7] = 1
步骤8: r = 5, a[8] = 1

因此,提醒是5 ,结果是000011111 = 31

我认为bc使用10 ^ n而不是2作为基数。因此,每个内部“数字”仅是n个十进制数字,至少对于十进制输入/输出,问题变得微不足道了。

无需使用幂运算:

#include "stdio.h"
#include "stdlib.h"
#include "string.h"

int main(){
    char a[] = "10011";
    unsigned long int res= 0;
    int i;

    for(i = 0; i < strlen(a); i++){
        res = (res<<1) + (a[i]-'0');
    }

    printf("%d",res);
    return 0;
}

第一次更新

现在长度应该不是问题了...

#include "stdio.h"
#include "stdlib.h"
#include "string.h"

char *doubles(char *);
char *sum(char *,int);

int main(){
    char a[] = "10011";
    char *res = calloc(2,sizeof(char));
    int i;

    res[0] = '0';
    for(i = 0; i < strlen(a); i++){
        res = sum(doubles(res),(a[i]-'0'));
    }

    printf("%s",res);
    return 0;
}

char *doubles(char *s){
    int i,len = strlen(s),t = 0;
    char *d;
    d = calloc(len+1,sizeof(char));
    for(i = 0; i < len; i++){
        t = ((s[len-i-1]-'0')<<1) + t;

        d[len-i] = ('0' + (t%10));
        t = t/10;
    }

    d[0] = t+'0';

    return (d[0] == '0')?d+1:d;
}

char *sum(char *s,int n){
    int i, len = strlen(s),t = n;
    char *d = calloc(len+1,sizeof(char));

    for(i = 0; i < len ; i++){
        t = (s[len-i-1]-'0') + t;
        d[len-i] = ('0' + (t%10));
        t = t/10;
    }
    d[0] = t+'0';

    return (d[0] == '0')?d+1:d;
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM