或者您可以使用此页面上描述的吸血鬼数字的属性(从 Wikipedia 链接):
Pete Hartley 发现的一个重要理论结果:
If x·y is a vampire number then x·y == x+y (mod 9)
证明:设 mod 为二进制模运算符,d(x) 为 x 的十进制数字之和。众所周知,对于所有 x,d(x) mod 9 = x mod 9。假设 x·y 是吸血鬼。然后它包含与 x 和 y 相同的数字,特别是 d(x·y) = d(x)+d(y)。这导致: (x·y) mod 9 = d(x·y) mod 9 = (d(x)+d(y)) mod 9 = (d(x) mod 9 + d(y) mod 9) mod 9 = (x mod 9 + y mod 9) mod 9 = (x+y) mod 9
同余的解是 (x mod 9, y mod 9) in {(0,0), (2,2), (3,6), (5,8), (6,3), (8, 5)}
所以你的代码可能看起来像这样:
for(int i=18; i<100; i=i+9){ // 18 is the first multiple of 9 greater than 10
for(int j=i; j<100; j=j+9){ // Start at i because as @sh1 said it's useless to check both x*y and y*x
checkVampire(i,j);
}
}
for(int i=11; i<100; i=i+9){ // 11 is the first number greater than 10 which is = 2 mod 9
for(int j=i; j<100; j=j+9){
checkVampire(i,j);
}
}
for(int i=12; i<100; i=i+9){
for(int j=i+3; j<100; j=j+9){
checkVampire(i,j);
}
}
for(int i=14; i<100; i=i+9){
for(int j=i+3; j<100; j=j+9){
checkVampire(i,j);
}
}
// We don't do the last 2 loops, again for symmetry reasons
由于它们是每个集合中的 40 个元素,例如{(x mod 9, y mod 9) = (0,0); 10 <= x <= y <= 100}
,因此您只进行4*40 = 160
迭代,当蛮力为您提供 10^4 次迭代时。如果考虑到>= 1000
约束,您可以执行更少的操作,例如,您可以避免检查 if j < 1000/i
。
现在您可以轻松放大以找到超过 4 位数的吸血鬼 =)