2

次のIEnumerableLINQクエリがあります。

var query = from p in Enumerable.Range(2, 1000000)
let sumofPowers = from ch in p.ToString()
                  let sumOfPowers = Math.Pow(Convert.ToDouble(ch.ToString()), 5)
                  select sumOfPowers
where p == sumofPowers.Sum()
select p;

それはそれらの桁の五乗の合計として書くことができるすべての数の合計を見つけます。プロジェクトオイラー問題30です

そのままで問題なく動作します。私はそれがニッチであることを知っています、しかし範囲は私を悩ませます。基本的には1,000,000で正しい結果が得られたと推測しているので、そこで停止させます。このシナリオでは、数は十分でした。

ただし、これはハードコードされた「乱数」にすぎません。コードを見ると、どこp == sumofPowers.Sum()が真であるかすぐに、ループを実際に実行する必要がなくなっていることがわかります。

私はyield他の状況でそれを行うことができbreak、通常のループで動作することを知っています-それで、この状況であなたができることはありますか?

4

3 に答える 3

4

First()演算子を使用してブレークアウトできます。

LINQは遅延計算を行うため、これはp == sumofPowers.Sum()のポイントに到達するまで続き、最初の要素を返します。クエリ全体を(...)。First();でラップするだけです。最初の値を返します。

また、その間、文字列に変換してからdoubleに変換する必要はありません。int-> doubleから直接変換でき、文字列の変換を回避できます。

于 2009-04-25T18:33:27.367 に答える
1
class Program
{
    static void Main(string[] args)            
    {
        ulong sum, gh = 0;

        for (ulong i = 2; i <= 355000; i++)
        {
            string s = Convert.ToString(i);
            sum = 0;
            int ddd = s.Length;
            for (int j = 0; j < ddd; j++)
            {
                //sum +=(int)Math.Pow(Convert.ToInt32(s[j]), 4);
                ulong g = Convert.ToUInt64(Convert.ToString(s[j]));
                sum = sum + (ulong)Math.Pow(g, 5);
            }
            // Console.WriteLine(sum);
            if (sum == i)
            {
                gh += i;
            }
        }
        Console.WriteLine(gh);

        Console.ReadKey();
    }
}
于 2011-07-17T18:52:34.933 に答える
0

LINQはすべての問題の解決策ではありません。問題にはそのソリューションによって定義される範囲しかないため、「クエリ」の観点からは範囲がないため、これはLINQや標準のIEnumerable拡張メソッドなどの既知のセット操作には適していません。イールドステートメントを使用すると、より良い結果が得られます(そしてより読みやすいコードが生成されます)。

于 2009-04-25T18:32:47.587 に答える