- 01
- 02
- 03
- 04
- 05
- 06
- 07
- 08
- 09
- 10
- 11
- 12
- 13
- 14
- 15
- 16
#include <stdio.h>
float abs(float a) { return a > 0 ? a : -a; }
int main() {
float x, e, step = 1, summ = step;
int i = 0;
scanf("%f, %f", (printf("x, e: "), &x), &e);
do summ += (abs(step *= x / ++i) > e) ? step : 0; while (abs(step) > e);
printf("summ = %f\n", summ);
return 0;
}
TheCalligrapher 16.04.2012 01:41 # +4
Также стоит заметить, что основаная говнокодовость в данном случае заключается даже не в говностилистике кода, а нарушении классического правила работы с плавающими типами, известного каждому первокласснику: накопительное суммирование в плавающем аккумуляторе всегда следует начинать с минимальных по модулю значений.
guest 16.04.2012 23:51 # 0
Имхо, тут оценка погрешности шагом - слишком топорно (не работает для x > 0).
И 2 сравнения в цикле - перебор.
По поводу "аккумулятора", вы предлагаете отсортировать ряд? Кэп намекает, что a(n+1) / a(n) = x / n+1 => ошибка в малых разрядах не успеет накопиться. К тому же, в данном случае существует оценка для остаточного члена (для удобства можно предварительно frexp). Или использовать отрицальные x, тогда, действительно, можно оценивать погрешность шагом.
TheCalligrapher 17.04.2012 03:33 # +1
Надо лишь сначала определить последний интересующий нас член, пусть даже "холостым" прогоном как в оригинальном коде...
guest 17.04.2012 10:38 # 0
Интересно, в каких-нибудь библиотеках так считают экспоненту.
TheCalligrapher 19.04.2012 21:09 # 0
WGH 19.04.2012 22:05 # +1
Ого!
guest8 09.04.2019 13:06 # −999