题目描述
4和7是两个幸运数字,我们定义,十进制表示中,每一位只有4和7两个数的正整数都是幸运数字。
前几个幸运数字为:4,7,44,47,74,77,444,447...
现在输入一个数字K,输出第K个幸运数。
输入
第一行一个数字T(T<=1000)表示测试数据的组数。对于每组测试数据,输出一个数K
输出
每组数据输出一行,第K个幸运数。
样例输入
3
5
100
1000000000
样例输出
74
744747
77477744774747744747444444447
分析:
我们发现4是第一个,7是第二个,44是第三个,47是第四个
不如将4看成0,7看成1,然后就得到二进制数了
4是0
7是1
可是44也变成0了,这就不太好了...于是想到在所有辛运数字前面加上7(也就是所有二进制前加一个1)这样我们就可以再列出一个表了:
4是10
7是11
44是100
47是101
74是110....哇真的是二进制诶.....所以直接将n像我那样拆分,就可以得到一个二进制串,再将二进制串变成十进制后减一即可。
/**
* 将4和7看成二进制0和1, 4->0 7->1
*
* 一位数有2个 pow(2,1)
* 4->0
* 7->1
*
* 2位数有4个 pow(2,2)
* 44->00
* 47->01
* 74->10
* 77->11
*
* 3位数有8个 pow(2,3)
* 444->000
* 447->001
* 474->010
* 477->011
* 744->100
* 747->101
* 774->110
* 777->111
*
* n位数有pow(2,n)个
*
* 求第k个幸运数,即求k的bits是几位数
* for (i;i++) {
* count += Math.pow(2,i);
* if (k <= count) {
* break;
* }
* }
* bits = i;
*/
代码:
public class Main
{
//求出第K个幸运数的“位数”
private static int getBits(int k)
{
int count=0;
int bit=0;
while(count<k)
{
++bit;
count+=Math.pow(2,bit);
}
return bit; } private static void slove(int[] arr)//static
{ for(int i=0;i<arr.length;i++)
{
int bits=getBits(arr[i]);
int addOne=arr[i]+1;
//将十进制数转化为二进制串
String bitStr=Integer.toBinaryString(addOne);
//将二进制串转化为字符数组;
char[] bitArr=bitStr.toCharArray();
//移除二进制串中的最高位的1
char[] reArr=new char[bits];
StringBuilder str=new StringBuilder(bits);
for(int j=0;j<bits;j++)
{
reArr[j]=bitArr[j+1];
//将01串变为47串
if(reArr[j]=='0')
{
str.append('4');
}
else
{
str.append('7');
} }//for System.out.println(str.toString());
} } public static void main(String[] args)
{
Scanner sc=new Scanner(System.in); while(sc.hasNextInt())
{
int arrayNum=sc.nextInt();
int[] inputNum=new int[arrayNum];
for(int i=0;i<arrayNum;i++)
{
inputNum[i]=sc.nextInt();
} slove(inputNum); }//while }
测试效果: