2017-03-25 3 views
1

ハスケルで次の合計を計算したいとします。(m + i)^ n from i = m to n。Haskellで再帰呼び出しを通して変数を維持する

sum2017 m n 
|m > n = 0 
|otherwise = (c + m)^n + sum2017 (m+1) n 
where c = m 

が、問題は、cが原因あなたは維持、ローカル関数の実際の再帰を詰め込むことができます再帰呼び出し

答えて

5

から新しい値を割り当てる取得するたびに変化することである。これまでのところ、私はこの考えていますc外結合:

sum2017 m = go m 
where go μ n 
     | μ > n  = 0 
     | otherwise = (c + μ)^n + go (μ+1) n 
     c = m 

...もちろん、あなたがして完全にc = mを省略することができ、ちょうど再帰で(m + μ)^nを使用しています。

この具体例

も簡単にHaskellで

sum2017 m n = sum [(m+μ)^n | μ<-[m..n]] 
1

のように、まったくマニュアル再帰なしで行うことができ、あなたは可能な限り明示的な再帰を避けたいです。

代わりに何をしますか?あなたはあなたのためにそれを行う機能をループ使用します。)

sum2017 m n = sum $ ((^ n) . (+ m)) <$> [m .. n] 

それとも、代わりにこのpointfreeのラムダ関数を使用することができます(\ X - >(C + X)^ n)の

あなたがすることを決定した場合leftaroundaboutが示唆したように、ローカルの機能を持っている、それはないグローバル関数に、自分自身に再帰ます:

sum2017 m = go m 
    where go μ n 
    | μ > n  = 0 
    | otherwise = (c + μ)^n + go (μ+1) n 
    c = m 

そうでないので、それはstackoverflowのに

+0

ようこそかなり速い制御/メモリから抜け出すことができます。良いアドバイスですが、この回答は、率直に言って、私のコメントや編集として投稿されています(十分な評判があれば、他の人の投稿にコメントできます)。このアプリケーションスタイルのマッピングが何をしているかを詳しく説明すれば、スタンドアロンの回答としてさらに価値があります。 (BTW、 '(^ n)。(+ m)'の周りに括弧は必要ありません。) – leftaroundabout

+0

私はこの投稿を削除して、あなたのコメントを書くべきではないと思いますか? マッピングとローカルバインドの再帰についての情報を追加しますか? (投稿時にはコメントできませんでした。私はちょっと控えてください) –

関連する問題