次にプロジェクトオイラーの問題233に取り組むことにしましたが、いくつかの大きな問題があります。私はいくつかの分析を行い、かなり良い進歩を遂げましたが、今は行き詰まっています。これが私の仕事です:
補題1:円は4つのコーナーポイントを通過するため、任意のnに対して少なくとも4つの解があります。しかし、円周上の各ポイントには、反射で見つかった他の7つのポイントがあります。したがって、常に8k+4の格子点があります。
補題2:円は半径(√2)nと中心(n / 2、n / 2)を持っているので、その方程式は(xn / 2)^ 2 +(yn / 2)^ 2 =[n/√2]^です。 2.2。これは、x ^ 2 + y ^ 2 = n(x + y)に減少します。
補題3:x ^ 2 + y ^ 2 = n(x + y)の解が(x、y、z)と書かれている場合、別の解は(kx、ky、kz)です。その証拠は次のとおりです。
(x+y)n = x^2+y^2
(kx)^2+(ky)^2 = (kx+ky)m
k(x^2+y^2) = (x+y)m
m = kn
これは私がその考えでしたのと同じくらいでした-私はそこから行くところをどこにも見ることができませんでしたが、それはよく役立つかもしれないので含まれています。
次の考えは、円の中心を動かすことでした。整数全体を任意の次元で動かす同じ数の解があります。したがって、n / 2が整数の場合、n = 2k、x ^ 2 + y ^ 2 = 2 * k^2となります。また、この方程式には、方程式x ^ 2 + y ^ 2 = k ^ 2と同じくらい多くの解があることがわかります(Sloane A046109を参照)。
これにより、 A046080を介して任意のnの解の数を計算する簡単な方法も得られます。4k+1の形式のnの素数の累乗がf[0]... f [m]の場合、解の数は4 * product(2f [i] +1 | i in [0. .. .m])。
これにより、逆方向に作業することができました。4.product(2f [i] +1 | i in [0 ... m])= 420なので、product(2f [i] +1 | i in [0 ... m] )= 105 = 3 * 5*7。私はこのプログラムを思いつくことができました。これは、420個の円格子点を持つ2kおよび10^11未満の形式ですべてのnの合計を見つけると思います。答え(私は願っています!)は257199853438240692です。
これがCプログラムです:
#include "stdlib.h"
#include "stdio.h"
#include "math.h"
#include "string.h"
#define lim 1000000000L
char prime[lim];
long primes[50000000];
long len = 0;
int main(void)
{
long i, j;
for(i = 0; i < lim; i++)
{
prime[i] = 1;
}
for(i = 2; i < lim; i++)
{
if(prime[i])
{
for(j = 2*i; j < lim; j += i) prime[j] = 0;
if((i-1)%4 == 0)
{
prime[i] = 2;
//printf("%li\n", i);
primes[len++] = i;
}
}
if(i < 1000 || (i < 10000 && i%1000 == 0) || i%10000 == 0) printf("%li, %li\n", i, len);
}
printf("primes!\n");
long a, b, c, v, total = 0, k;
for(a = 0; a < len; a++)
{
v = primes[a]*primes[a]*primes[a];
if(v > 50000000000L) break;
for(b = 0; b < len; b++)
{
if(b == a) continue;
v = primes[a]*primes[a]*primes[a]*primes[b]*primes[b];
if(v > 50000000000L) break;
for(c = 0; c < len; c++)
{
if(c == a) continue;
if(c == b) continue;
v = primes[a]*primes[a]*primes[a]*primes[b]*primes[b]*primes[c];
if(v > 50000000000L) break;
for(k = 1; k*v <= 50000000000L; k++)
{
if(prime[k] == 2) continue;
total += k*v;
}
}
}
}
for(a = 0; a < len; a++)
{
v = primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[a];
if(v > 50000000000L) break;
for(b = 0; b < len; b++)
{
if(b == a) continue;
v = primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[b]*primes[b]*primes[b];
if(v > 50000000000L) break;
for(k = 1; k*v <= 50000000000L; k++)
{
if(prime[k] == 2) continue;
total += k*v;
}
}
}
for(a = 0; a < len; a++)
{
v = primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[a];
if(v > 50000000000L) break;
for(b = 0; b < len; b++)
{
if(b == a) continue;
v = primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[a]*primes[b]*primes[b];
if(v > 50000000000L) break;
for(k = 1; k*v <= 50000000000L; k++)
{
if(prime[k] == 2) continue;
total += k*v;
}
}
}
printf("%li\n", 2*total);
return 0;
}
420個の円格子点を持ち2k+1の形式のnの値を追加する必要があります!しかし、それはn = 2kの場合よりも難しいようで、私はそれに対する方法を見つけることができません。方法がかなり複雑なので、nでも私の答えが正しいかどうかも少しわかりません...誰かがそれを確認できますか?異なるnを異なる方法で処理することなく、きちんとした方法はありますか?
私はすべてアイデアがありません!
ジョン・フェミネラが示唆しているように、N = 2kのときはできるので、私は主にN = 2k+1をどのように扱うかに興味があります。