SP8624 题解

· · 题解

SP8624 题解

科普时间

整型有 4 种进制形式:

  1. 十进制: 都是以 0\sim 9 这九个数字组成,不能以 0 开头。
  2. 二进制: 由 0 和 1 两个数字组成。
  3. 八进制: 由 0\sim7 数字组成,为了区分与其他进制的数字区别,开头都是以 0 开始。
  4. 十六进制:由 0\sim9 和 A\sim F 组成。为了区分于其他数字的区别,开头都是以 0x 开始。

一、十进制转换为二进制、八进制、十六进制

1、十进制转二进制

(1)十进制转二进制的转换原理:除以 2,反向取余数,直到商为 0 终止。

(2)具体做法: 将某个十进制数除 2 得到的整数部分保留,作为第二次除 2 时的被除数,得到的余数依次记下,重复上述步骤,直到整数部分为 0 就结束,将所有得到的余数最终逆序输出,则为该十进制对应的二进制数。

2、十进制转八进制

(1)转换原理:除以 8,反向取余数,直到商为 0 终止。

(2)具体步骤与二进制一样 例如:十进制数 796 转换成八进制数: 将 796 除 88 取得第一个余数为 4,将除 8 得到的整数部分 99 作为第二次的被除数,重复上述步骤,直至最终整数部分为0就结束。将取得的所有余数逆序输出 则为:796\to1434。

3、十进制转十六进制

(1)转换原理:除以 16,反向取余数,直到商为 0 终止。

(2)具体步骤也和二进制、八进制一样,重复上述做法即可得到十六进制数。 例如:十进制数 796 转换为十六进制数 即为:796 \to 31c。 需要注意的是,十六进制数是由 0\sim9 和 A\sim F (或者 a\sim f)组成的,A 相当于十进制中的 10,B 相当于 11,依次类推,F 相当与 15,上述事例中取得的余数 12 即为十六进制中的 c。

小结:以上几种进制的整数部分转换原理都是除进制数取余数,倒序输出。

4、八进制、十六进制、二进制的转化

原理:八进制数的一位是二进制数的三位,将每一位用三位二进制数表示。

原理:将二进制数转换为等值的十六进制数称为二-十六进制转换,采用的方法是“四位一组法”,因为四位二进制数恰好有 16 个状态,分别对应十六制数的 16 个数码。

也就是说,“四位一组法”就是从低位到高位依次将每 4 位二进制数划分为 1 组,高位不足 4 位的前面加 0 补足 4 位,然后将每 1 组用对应的十六进制数的数码表示,就得到相应的十六进制数。

将十六进制数转换为等值的二进制数称为十六-二进制转换。其转换方法刚好和二转十六相反,只要将十六进制数的每 1 位分别用 4 位二进制数表示即可。

题目分析

根据题意, 输入三个值 B,X,Y,每次询问求出 NimSum(X,Y) 在 B 进制下的异/值。

按照题目模拟,处理 X,Y 在 B 进制的最高位,然后逐一使用最大值转换即可。

UKE Code

#include<bits/stdc++.h>
using namespace std;
int t,p,b,x,y;
string xx1,xx2;
string uke(int a) {
    string zzy;
    while(a) {
        zzy+='0'+(a%b);
        a/=b;
    }
    return zzy;
}
int main() {
    cin>>t;
    while(t-1) {
        cin>>x>>p>>y>>b;
        xx1=uke(x);
        xx2=uke(y);
        if(xx2.size()>xx1.size())
            swap(xx1,xx2);
        int zrxsba=1,zzy=0;
        int asd1=xx1.size();
        int asd2=xx2.size();
        for(int i=0; i<asd2; i++)
            xx1[i]=((xx1[i]-'0'+xx2[i]-'0')%b)+'0';
        for(int i=0; i<asd1; i++) {
            zzy+=(zrxsba*(xx1[i]-'0'));
            zrxsba*=b;
        }
        cout<<p<<' '<<zzy<<endl;
    }
    return 0;
}
// by 1013713 10/14 09:55,2023
参考