藍橋杯: 基礎練習 十六進制轉八進制


 

問題描述
  給定n個十六進制正整數,輸出它們對應的八進制數。

輸入格式
  輸入的第一行為一個正整數n (1<=n<=10)。
  接下來n行,每行一個由0~9、大寫字母A~F組成的字符串,表示要轉換的十六進制正整數,每個十六進制數長度不超過100000。

輸出格式
  輸出n行,每行為輸入對應的八進制正整數。

  【注意
  輸入的十六進制數不會有前導0,比如012A。
  輸出的八進制數也不能有前導0。

樣例輸入
  2
  39
  123ABC

樣例輸出
  71
  4435274

  提示
  先將十六進制數轉換成二進制數,再由二進制數轉換成八進制。

 

 

PS:這里測試的十六進制數特別大,所以要用數組來處理和運算

#include<iostream>
#include<string.h>
#include<math.h>
using namespace std;
char str[1000005], er[4000020], ch[4]; //str數組儲存輸入的十六進制數 er儲存對應的二進制數 ch是一個臨時數組
int b[1000005];
int main()
{
    char a[17] = "0123456789ABCDEF";
    int  t;
    cin >> t;
    while (t--)
    {
        int i = 0, len;
        memset(str, 0, sizeof(str));
        cin >> str;
        len = strlen(str);
        if (str[0] == '0')//如果輸入只有一個0
            cout << '0' << endl;
        else
        {
            for (int j = 0; j<len; j++)
            {
                for (int k = 0; k < 18; k++)
                {
                    if (str[j] == a[k])
                    {
                        int temp, kk = 0, flag = 0;
                        while (k)//將十六進制數轉換為二進制數
                        {
                            ch[kk++] = a[k % 2];//這里是將十六進制數的每一位數字轉換成長度為四的二進制數
                            k /= 2;
                            flag = 1;
                        }
                        if (flag == 0)//特殊處理0,將0轉換為二進制數
                        {
                            for (int j = 0; j < 4; j++)
                                ch[j] = '0';
                        }

                        temp = kk % 4;
                        if (temp != 0)//補零
                        {
                            for (int j = 1; j <= 4 - temp; j++)
                                ch[kk++] = '0';
                        }
                        for (int j = 3; j >= 0; j--)
                        {
                            er[i++] = ch[j];
                        }
                        break;
                    }
                }
            }

            //在二進制轉換為八進制之前,要將二進制數中的前導零去掉
            int f, temp = 0;
            while (er[0] == '0')
            {
                for (int j = 0; j < i; j++)
                {
                    er[j] = er[j + 1];
                }
                temp++;
            }
            i = i - temp;
            f = i % 3;
            //如果二進制數的長度不是3的整數,要在二進制數前補0
            if (f != 0)
            {
                for (int j = i + 1; j >= 3-f; j--)//數組整體后移3-f個位置
                    er[j] = er[j - 3 + f];
                for (int j = 0; j < 3 - f; j++)
                    er[j] = '0';
                i = i + 3 - f;
            }
            int w = 0;
            //以下是將二進制數轉換為八進制數
            //一個八進制數等於三個二進制數
            for (int j = 0; j <i; j = j + 3)//注意j的初值是否正確
            {
                int sum = 0;
                for (int q = 0; q<3; q++)
                {
                    sum = sum + (er[j + q] - '0') * pow(2, 3 - q - 1);
                }
                b[w++] = sum;
            }
            for (int h = 0; h < w; h++)
            {
                if (b[0] == 0)
                    continue;
                cout << b[h];
            }
            cout << endl;
        }
    }
}

 

簡化版

#include <iostream>
#include <string>
using namespace std;
 
int main()
{
    int n;
    cin>>n;
    for(int k=1;k<=n;k++)
    {
        string s1,s2;//s1為輸入的原始的十六進制串,s2為轉化成的二進制串
        cin>>s1;
        s2="";//初始化
        for(int i=0;i<s1.length();i++)//遍歷,字符串上加上每一位
        {
            switch(s1[i])
            {
                case '0':s2+="0000";break;
                case '1':s2+="0001";break;
                case '2':s2+="0010";break;
                case '3':s2+="0011";break;
                case '4':s2+="0100";break;
                case '5':s2+="0101";break;
                case '6':s2+="0110";break;
                case '7':s2+="0111";break;
                case '8':s2+="1000";break;
                case '9':s2+="1001";break;
                case 'A':s2+="1010";break;
                case 'B':s2+="1011";break;
                case 'C':s2+="1100";break;
                case 'D':s2+="1101";break;
                case 'E':s2+="1110";break;
                case 'F':s2+="1111";break;
                default:break;
            }
        }
        int len=s2.length();
 
        if(len%3==1)//三個二進制為一位八進制,二進制串前面補0,確保二進制串的長度為3的倍數
            s2="00"+s2;
        else if(len%3==2)
            s2="0"+s2;
        int flag=0;
        for(int i=0;i<=s2.length()-3;i+=3)
        {
            int num=4*(s2[i]-'0')+2*(s2[i+1]-'0')+(s2[i+2]-'0');
            if(num)
                flag=1;//忽略前導0
            if(flag)
                cout<<num;
        }
        cout<<endl;
    }
    return 0;
}

 

延伸拓展:任意進制轉換


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM