日期:2014-05-20  浏览次数:20678 次

java 爱好者 来 看看 这道题 怎么做啊
吸血鬼数字是指位数为偶数的数字,可以又一对数字相乘而得到,而这对数字各包含乘积的一半位数的数字,其中从最初的数字中选取的数字可以任意排序,以两个0结尾的数字是不允许的,例如,下列的数字都是吸血鬼数字:
  1260=21*60
  1827=21*87
  2187=27*81
写个程序吗,找出4位数的所有吸血鬼数字

------解决方案--------------------
Java code
import java.util.Arrays;

public class Tt {

    public static void main(String[] args) {
        Tt t = new Tt();
        t.vampireNumber();
    }

    public void vampireNumber() {
        for (int i = 10; i < 100; i++) {
            for (int j = 10; j < 100; j++) {
                int product = i * j;
                if (product > 1000 && product < 10000 && product % 100 != 0 && isEqual(product, i, j)) {
                    System.out.println(product + "=" + i + "*" + j);
                }
            }
        }
    }

    public boolean isEqual(int product, int i, int j) {
        char[] num1 = ("" + product).toCharArray();
        char[] num2 = ("" + i + j).toCharArray();
        Arrays.sort(num1);
        Arrays.sort(num2);
        return Arrays.equals(num1, num2);
    }
}

------解决方案--------------------
for example
思路,从1001到9999循环,取出每位数字进行排列组合,把排列组合的结果的前半部和后半部拆开,判断前半部和后半部的乘积是否合循环数一致

Java code
import java.util.*;
public class Test {   
    public static void main(String[] args) throws Throwable {
        int num[] = {1, 0, 0, 1}; //循环数,从1001到9999循环,因为要取每个数字,所以直接采用数组
        int idx[] = {0, 1, 2, 3}; //初始排列组合下标
        int dig[] = Arrays.copyOf(idx, idx.length); //排列组合用下标
        int sum, m1, m2, chk;
        while (num[0] < 10) {
            sum = 0;
            for (int i=0; i<num.length; i++) {
                sum = sum*10 + num[i]; //计算循环数没,如{1,0,0,1}得到1001
            }

            if (sum % 100 != 0) { //如果循环数不以两个0结尾
                System.arraycopy(idx, 0, dig, 0, idx.length); //获得排列组合下标
                while (dig[0] < num.length) { //循环排列组合下标,直到排列组合结束
                    chk = 0;
                    for (int i=0; i<dig.length && chk==0; i++) {
                        for (int j=i+1; j<dig.length; j++) {
                            if (dig[i] == dig[j]) {
                                chk = 1; //判断是否存在重复的下标,存在则为不合法的组合
                                break;
                            }
                        }
                    }
                    if (chk == 0) { //如果是合法组合
                        m1 = 0;
                        for (int i=0; i<dig.length; i++) {
                            m1 = m1*10 + num[dig[i]];
                        }
                        m2 = m1 % 100; //取出组合结果的前半部和后半部
                        m1 /= 100;
                        if (m1 > 9 && m2 > 9 && sum == m1*m2) { //如果满足题目要求则打印
                            System.out.printf("%d=%d*%d\n", sum, m1, m2);
                            break; //找到一个结果就退出,否则会出现重复,即m1*m2和m2*m1
                        }
                    }

                    dig[dig.length-1]++; //排列组合下标进位
                    for (int i=dig.length-1; i>0; i--) {
                        if (dig[i] == num.length) {
                            dig[i] = 0;
                            dig[i-1]++;
                        } else {break;}
                    }
                }
            }

            num[num.length-1]++; //循环数增加,如1001变为1002
            for (int i=num.length-1; i>0; i--) { //判断是否发生进位
               if (num[i] == 10) {
                    num[i] = 0;
                    num[i-1]++;
                } else {break;}
            }
        }
    }
}