题解:B3869 [GESP202309 四级] 进制转换
_VirtualPoint_ · · 题解
声明(也就是废话)
- 一审打回,感谢一审管理员Jiyuu_no_Tsubasa的审核。
- 二审打回,感谢二审管理员swiftc的审核。
- 这是本蒟蒻的第一篇题解,激动不已。三审管理员求过~
- 代码请需要的同学谨慎使用。切勿抄题解!这是非常不道德的行为。而且,这还可能导致又一位作弊者的产生。
题目大意
输入
分析
相信大家早就发现了,题目良心得给出了转换方法!
这里放上原文:
“对于任意一个
L 位K 进制数,假设其最右边的数位为第0 位,最左边的数位为第L-1 位,我们只需要将其第 i 位的数码乘以权值K^i ,再将每位的结果相加,即可得到原K 进制数对应的十进制数。”
什么意思呢?
这里涉及到一个概念:位权。
什么是位权呢?我们拿一个十进制数
| 类型 | 十万位 | 万位 | 千位 | 百位 | 十位 | 个位 |
|---|---|---|---|---|---|---|
| 数字 | ||||||
| 位权 | ||||||
| 计算过程 | ||||||
| 实际数值 |
而
相信大家有思路了吧!第
这是十进制中的位权。但如果这个
| 类型 | 十万位 | 万位 | 千位 | 百位 | 十位 | 个位 |
|---|---|---|---|---|---|---|
| 数字 | ||||||
| 位权 | ||||||
| 计算过程 | ||||||
| 实际数值 |
这几个数值加起来,刚好就是八进制数
着手实现
看到这里,相信大家都明白怎么写代码了吧!但是还有几个易错点我要讲一讲。
string!
如果你想用 int 类型输入,随后用 while 循环拆分数位累加的话,那你可就大错特错了。虽然用这种方式拆分数位又快又好用,但是你想过没有,int 类型似乎不支持除了 1~10 以外的数字输入啊!
而这些数字(包括但不限于 A)可是 11~16 以及更多进制的命根子!
我们只能用 string 来实现。当然,如果你学有余力,不妨挑战一下字符数组?
long long!
正所谓那句老话:
“十年 OI 一场空,不开 long long 见祖宗!”
我们可以想一下,如果题目输入十六进制数 int 类型撑爆!就算是 long 类型也很危险!
只能开 long long 了对吧?
当然,如果题目数据再大一点,我们就不得不用到 __int128 了。
代码
#include <iostream>
#include <cmath>
using namespace std;
long long n;
long long k;
long long num[15];
string snum;
int main() {
cin >> n;//处理输入
while (n--) {
cin >> k >> snum;//处理输入
long long ans = 0;
for (long long i = 0; i < snum.size(); i++) {
if (!(snum[i] >= '0' && snum[i] <= '9')) {
num[i] = snum[i]-'A'+10;
} else {
num[i] = snum[i]-'0';
}
ans = ans * k + num[i];
//我们可以直接在处理字符的时候直接进行累加。
//当然,更直接的做法就是不要num数组,直接处理完后累加。
}
cout << ans << endl;//记得输出!
}
return 0;
}
大家看看,AC的非常漂亮是不是?