Си, рекуррентное вычисление

Задано натуральное число n, действительное число x. Вычислить: введите сюда описание изображения

Моя неудачная попытка:

#include <stdio.h>
#include <math.h>
#include <locale.h>

int main() {
    setlocale(0, "");

    unsigned int n;
    float x;
    float y = 0;

    printf("Задайте числа n и x:\n");
    scanf("%u%f", &n, &x);

    int k;
    for (k = 1; k <= n; ++k)
    {
        y += (k / k + 1) - powf( cosf( fabsf(x)), k);
    }

    printf("%f\n", y);

    return 0;
}

Неудачная т.к. рекуррентное вычисление более оптимальное чем вычисления на каждой итерации (у меня получается только так). Как я могу переписать данный код, чтобы вычисления происходили рекуррентно?


Ответы (1 шт):

Автор решения: Harry

Для начала преобразуем ряд:

введите сюда описание изображения

Ну, а потом уже будет ерундой его вычисление, особенно если вспомнить, что cos - функция четная :):

double s(double x, int n)
{
    double c = cos(x), z = 0;
    c = n - c*(pow(c,n)-1)/(c-1);
    for(int i = n; i >= 1; --i)
        z += 1./(i+1.);
    return c-z;
}

Обратите внимание на скобки в дроби в отличие от вашего (k / k + 1), каковое всегда 2, да и на точки возле 1 (чтоб деление не было целочисленным).

Ага, пока писал, вы добавили необходимость рекуррентности. Ну что ж, тогда ряд считаем рекуррентно...

double fr(int k)
{
    if (k==1) return 1./2.;
    else return 1./(k+1.)+fr(k-1);
}

double s(double x, int n)
{
    double c = cos(x);
    c = n - c*(pow(c,n)-1)/(c-1);
    return c-fr(n);
}

Можно (по большому счету, нужно :)) отдельно обработать случай, когда cos(x)==1.

Еще один вариант...

double sum(int n, double x)
{
    double s = 0;
    double a = 0, b = 1, c = cos(x);
    for(int k = 1; k <= n; ++k)
    {
        a += 1.0/k/(k+1);
        b *= c;
        s += a - b;
    }
    return s;
}
→ Ссылка