【题目链接】
ybt 1082:求小数的某一位
OpenJudge NOI 小学奥数 7830:求小数的某一位
【题目考点】
1. 数制:求某小数位
设
r
r
r为a/b的余数,q是整数商,那么根据
a
÷
b
=
q
⋯
⋯
r
a \div b = q \cdots\cdots r
a÷b=q⋯⋯r
有
a
b
=
q
+
r
b
\frac{a}{b} = q + \frac{r}{b}
ba=q+br
其中q是结果的整数部分,
r
b
\frac{r}{b}
br是结果的小数部分。
假设
r
b
\frac{r}{b}
br值为
0.
d
1
d
2
d
3
d
4
.
.
.
0.d_1d_2d_3d_4...
0.d1d2d3d4...其中
d
i
d_i
di是每一位的数字。
根据按位权展开公式,有:
r
b
=
d
1
⋅
1
0
−
1
+
d
2
⋅
1
0
−
2
+
d
3
⋅
1
0
−
3
.
.
.
\frac{r}{b} = d_1\cdot10^{-1}+d_2\cdot10^{-2}+d_3\cdot10^{-3}...
br=d1⋅10−1+d2⋅10−2+d3⋅10−3...
两边乘以10,有:
10
r
b
=
d
1
+
d
2
⋅
1
0
−
1
+
d
3
⋅
1
0
−
2
.
.
.
\frac{10 r}{b} = d_1+d_2\cdot10^{-1}+d_3\cdot10^{-2}...
b10r=d1+d2⋅10−1+d3⋅10−2...
10
r
b
的
余
数
是
(
10
r
)
%
b
\frac{10r}{b}的余数是(10r)\%b
b10r的余数是(10r)%b
这个数的整数部分是
10
r
−
(
10
r
)
%
b
b
=
d
1
\frac{10r - (10r) \% b}{b} = d_1
b10r−(10r)%b=d1,
小数部分:
(
10
r
)
%
b
b
=
d
2
⋅
1
0
−
1
+
d
3
⋅
1
0
−
2
.
.
.
\frac{(10r) \% b}{b} = d_2\cdot10^{-1}+d_3\cdot10^{-2}...
b(10r)%b=d2⋅10−1+d3⋅10−2...
得到的
d
1
d_1
d1,即为十分位数字。
同样地,将
(
10
r
)
%
b
b
\frac{(10r) \% b}{b}
b(10r)%b再乘以十,并分离整数部分,得到的就是百分位数字。
由此,总结出求小数各位数字的方法是:乘十取整。
求第n位小数,就是乘十取整10次后,最后一次取整得到的整数。
2. (扩展)数制:求某位的数字
求任意进制数字整数部分某位的方法是:除基取余
求任意进制数字小数部分某位的方法是:乘基取整
其中“基”是指该数制的基数,如十进制的基数是10,十六进制的基数是16。
2. 模拟:除法竖式
除法竖式本质上就是上述运算。但一般学生对除法竖式更为了解,所以以模拟除法竖式的角度来解题也可以。
- 设被除数为r,使r = a%b,作为最初的被除数,除数还是b。
- 被除数r比除数b小,r乘以10,然后求r/b,得到的商写在商的位置,即为十分位的值,得到的余数作为新的被除数。
- 此时被除数r比除数b小,r乘以10,然后求r/b,得到的商即为百分位的值,得到的余数作为新的被除数。
- 不断循环,第n次循环求出的商即为小数点后第n位。
【解题思路】
1. 以数制中“乘10取整”的思路来做
2. 以模拟除法竖式的角度来做
两种思路写出来的代码实际是一样的。
【题解代码】
解法1:数制:乘基取整
解法2:模拟除法竖式
#include<bits/stdc++.h>
using namespace std;
int main()
{
int a, b, n, d;//d为某一位的数字
cin >> a >> b >> n;
int r = a % b;//初始的被除数
for(int i = 1; i <= n; ++i)
{
r *= 10;//被除数乘以10
d = r / b;//求出此次相除得到的商,即为第i位的数字
r %= b;//余数作为新的被除数
}
cout << d;
return 0;
}