- 締切済み
再帰呼出しによる自然対数を求めるプログラム
題名そのままです。再帰によって階乗を求めるプログラムは書けたのですが、自然対数になると値をプラスしていくところでこんがらがってしまいます。助けてくださいお願いします。
- みんなの回答 (4)
- 専門家の回答
みんなの回答
- BLUEPIXY
- ベストアンサー率50% (3003/5914)
>自然対数の底 なるほど、 とりあえずサンプルとなるようなプログラムを呈示するのは、(実用になるかはともかく^^;)簡単ですが、質問の大意は、再帰を使った和の求め方だったと思うので、#1が参考になるかとと思います。 e=1+1/1!+1/2!+1/3!…1/n! で、能率を考えなければ n!=fact(n)で既に求めることができるのだから e=1+Σ[k=1からnまでの和]1/fact(n) f(n)=1/1!+1/2!+1/3!…1/n! ですが、とりあえず、f(n)という関数が定義できたとすると、 f(n)=f(n-1)+1/n! というのがわかると思います。 要するにn-1番目までの和が既に求まっていれば、 n番目までの和は n-1番目までの和+n番目の数になります。 要するに、このf(n-1)の部分が再帰呼び出しということになります。 f(n-1)は、 f(n-1)=f((n-1)-1)+ 1/(n-1)!で f(n-1-1-1…)となっていきますが、 n=1でこれ以上前には戻れなくなるので、値が1に決定し、逆に(後ろに戻って)全体の値が決定することになります。 なので、再帰的な関数では、まず終了条件によって値が確定し返すことを書いてから、終了しないときは、再帰的に(問題を小さくして)呼び出します。 つまり、 double f(int n){ if(n==0)return 0; return 1.0/fact(n)+f(n-1); } のような形になります。 この場合 e=1+f(n); 実際には、計算の精度や能率を考慮しないといけません。
- ency
- ベストアンサー率39% (93/238)
答え書いてしまうのも、どうかと思いますので、とりあえず、私の場合の考え方だけ。 ------------------------------------------------ n=0: f(0) = 1 n=1: f(1) = 1 + 1/1! = f(0) + 1/1! n=2: f(2) = 1 + 1/1! + 1/2! = f(1) + 1/2! n=3: f(3) = 1 + 1/1! + 1/2! + 1/3! = f(2) + 1/3! …… よって、次のように書けそうだ。 n>=1 の場合 f(n) = f(n-1) + 1/n! n=0 の場合 f(0) = 1 ------------------------------------------------ あとは、これは再帰の形でプログラムしてみれば良いと思います。 # はずしていたら、ごめんなさい。。。 # n! の部分は、作成済みの階乗の関数を流用すれば良いと思います。 ## ここまでいったら、ほぼ回答してしまっているのと同じかもしれませんね。 まずは、こんな感じでいかがでしょうか?
- BLUEPIXY
- ベストアンサー率50% (3003/5914)
{(x-1)/(x+1)}の2乗を掛けていく方がいいかも?
- BLUEPIXY
- ベストアンサー率50% (3003/5914)
math.h log() を使いましょうって 再帰にする理由がよくわからないのですが、 多分級数表現をプログラムするということなのでしょうが、どういう式を、どういうふうにプログラムしようとしているのですか? まあ、こんな感じかな? #include <stdio.h> #include <math.h> double add(double x, int k){ int n=2*k-1; if(k==0)return(0.0); return(pow((x-1)/(x+1), n)/n + add(x, k-1)); } void main(){ double x=5.0; x=add(x,20)*2.0; printf("f(5.0)≒%f\n",x); }
お礼
ありがとうございます!! 式はe=1+1/1!+1/2!+1/3!…1/n! という式です! 自分でnの値は自分でscanfして入力します。 BLUEPIXYさんの式でやってみたところ、17あたりで自然対数の値が2.71828182845・・・を超えてしまいます。自分のやり方が違っていたらすみません。
お礼
すいません!自然対数ではなく「自然対数の底」でした!申し訳ありません。