使用对数或其他方法将任何基数转换为C中的另一个基数

时间:2018-09-16 14:20:43

标签: c algorithm data-structures base converters

我正在尝试编写C程序,将给定基数的数字转换为任何其他基数(例如,将基数2的二进制数转换为基数8,或将基数3转换为基数16十六进制)。我对此进行了相当多的研究,并且已经通读了类似的文章The math behind converting from any base to any base without going through base 10?],但是在给出的说明中,他们使用了数组,但我不允许对此程序执行此操作。

没有为基础转换的每种可能组合编写带有方法的冗长程序,我看不到没有数组来存储可能的值怎么可能。我确实知道基本公式的对数有所更改,这使我可以在数字基数之间进行更改,但是我不清楚如何应用此方法,因为此公式仅给出了十进制数字答案,我仍然需要转换。

int log_base_n(int n, int logof)
{
    double logBaseN = log10((double) logof) / log10((double) n);
    return (int) ceil(logBaseN);
}

这是我尝试将二进制转换为十进制的中间步骤:

/**
* Convert decimal numbers to binary. Uses a greedy subtraction
* algorithm. Assumes max integer allowed is 2 to 16 power.
*
* @param numberToConvert
*/
void decToBin(int numberToConvert)
{
int power = 16;
double ans = pow(2, power);

if (numberToConvert > ans)
{
    printf("ERROR: Number too large to convert!\n");
    return;
}

while (ans > numberToConvert)
{
    power--;
    ans = pow(2, power);
}

printf("%d", 0);

int i = power;

while (i >= 0)
{

    ans = pow(2, i);
    numberToConvert = numberToConvert - ans;
    printf("%d", 1);
    i--;

    while ((pow(2, i) > numberToConvert) && (i >= 0))
    {
        printf("%d", 0);
        i--;
        ans = pow(2, i);
    }
   }
}

我知道Java有一个parseInt()方法,该方法可以进行基本转换,但是我可以在C中实现类似的功能,而不必像上面的方法那样为每种可能的转换编写方法,同时仍然使用对数相关的方法。理念?任何帮助将不胜感激。

1 个答案:

答案 0 :(得分:1)

  

但是我是否可以在C中实现类似的功能,而不必像上面的代码那样为每种可能的转换编写方法,同时仍然利用对数相关的思想?

对数是一个糟糕的选择。代码中日志的计算与数学上的日志不完全相同,并且会导致输出错误。

如果商的值略高于整数期望值,则下面是一个问题。当然,log10()对于logof <= 0是个问题。

double logBaseN = log10((double) logof) / log10((double) n);
return (int) ceil(logBaseN);

此外,log_base_n()的计算是完全不必要的。

这是一个整数问题。使用整数数学。


一个简单的非数组解决方案“要从任何碱基转换为另一个碱基” 1 就是使用递归。

void print_int_base(int numberToConvert, int base) {
  // For now, assume numberToConvert >= 0, 2 <= base <= 36
  if (numberToConvert >= base) {
    print_int_base(numberToConvert/base, base);
  }
  int digit = numberToConvert%base;
  int c = digit < 10 ? digit + '0' : digit + 'A';
  putchar(c);
}

测试代码

#include <stdio.h>

void print_int_base_test(int numberToConvert, int base) {
  printf("%10d %2d:", numberToConvert, base);
  print_int_base(numberToConvert, base);
  puts("");
}

int main() {
  int numberToConvert = 42;
  for (int base=2; base<=20; base++) {
    print_int_base_test(numberToConvert, base);
  }
}

输出

42  2:101010
42  3:1120
42  4:222
42  5:132
42  6:110
42  7:60
42  8:52
42  9:46
42 10:42
42 11:39
42 12:36
42 13:33
42 14:30
42 15:2M
42 16:2K
42 17:28
42 18:26
42 19:24
42 20:22

1 OP的转换思路显然是以各种形式打印int