之前在oj上做過,今天做藍橋杯基礎練習又遇到了這題
but沒有一遍AC
基礎練習 十六進制轉八進制
時間限制:1.0s 內存限制:512.0MB
提交此題 錦囊1 錦囊2
問題描述
給定n個十六進制正整數,輸出它們對應的八進制數。
輸入格式
輸入的第一行爲一個正整數n (1<=n<=10)。
接下來n行,每行一個由09、大寫字母AF組成的字符串,表示要轉換的十六進制正整數,每個十六進制數長度不超過100000。
輸出格式
輸出n行,每行爲輸入對應的八進制正整數。
【注意】
輸入的十六進制數不會有前導0,比如012A。
輸出的八進制數也不能有前導0。
樣例輸入
2
39
123ABC
樣例輸出
71
4435274
【提示】
先將十六進制數轉換成某進制數,再由某進制數轉換成八進制。
AC代碼:
#include <stdio.h>
#include <string.h>
#include <math.h>
char a[100002];
int b[400005],c[200002];
int k;
void add_0(int len)
{
int z = 4*len%3;//沒位16進制可以用4位二進制表示
k = 3 - z;
/*
k爲化爲二進制後應該補的零個數,
因爲之前初始化已經全是0,
所以之後的二進制數只要從k開始存就行。
*/
}
//十六進制字符化爲10進制數字
int num_16(char a)
{
if(a >= 'A')
return a - 'A' + 10;
else
return a - '0';
}
//每個10進制化爲2進制
void num_2(int len)
{
for(int i = 0; i < len; i++)
{
int f = 3,y = num_16(a[i]),t;
//核心部分,可以自己演示一遍
while(f >= 0)
{
t = y/pow(2,f);
if(t)
{
b[k++] = 1;
}
else
{
b[k++] = 0;
}
y %= (int)pow(2,f);
f--;
}
}
}
//打印8進制數
void print_8()
{
int j = 0,m = 0;
//每三位一個8進制數
for(int i = 2; i < k; i+=3)
{
c[j++] = b[i] + b[i-1]*2 + b[i-2]*4;
}
//去掉前置0
while(c[m]==0)
{
m++;
}
for(int i = m; i < j; i++)
printf("%d",c[i]);
printf("\n");
}
int main()
{
int n;
scanf("%d",&n);
while(n--)
{
memset(a,'\0',sizeof(a));
memset(b,0,sizeof(b));
memset(c,0,sizeof(c));
scanf("%s",a);
int len = strlen(a);
k = 0;//這個要注意,不要放外面去了
add_0(len);
num_2(len);
print_8();
}
return 0;
}