Update

Mar 28, 2018 14:11

К задаче.

Уменьшил требуемую абсолютную погрешность до
Read more... )

техническое, математика, численные методы, задачка, программирование

Leave a comment

Comments 18

Самый интересный для меня момент son_0f_morning March 28 2018, 13:03:52 UTC
Что суммирования с конца оказалось достаточно при вычислении рядов и боле-менее разумной точности.

Это далеко не тривиальный момент, особенно если учесть, что в FP и абсолютная и относительная погрешности расположены неравномерно (грубо говоря в 3ке подряд идущих чисел могут быть два разных интервала).

Reply

Re: Самый интересный для меня момент ahiin March 28 2018, 13:06:55 UTC
Я, кстати, подумал тут, что по сути ваш подход и мой (2002 года) вполне близки в итоге, просто мой вариант выражен более аналитически.
В пятницу выложу и теорию и код.

Reply

Re: Самый интересный для меня момент son_0f_morning March 28 2018, 13:11:05 UTC
Мой какой?
С квадратом точности и рядом эйлера или с кубом точности и интегралом?

ПС
С рядом эйлера -- это вроде то же самое, что вы закрыли вчера. Только у меня "погрешность" в явном виде прибавляется в коде, а в закрытом комменте она внесена в член ряда.

Reply

Re: Самый интересный для меня момент ahiin March 28 2018, 13:22:28 UTC
Тот вариант, что в виде исходника.

Reply


Общие соображения №2 (да простит меня автор) son_0f_morning March 29 2018, 09:25:39 UTC
Вообще я не занимаюсь научными рассчётами (очень редко -- исключительно редко надо было что-то посчитать по работе, ну и в студенчестве). Поэтому если я напишу явную чушь -- прошу меня понять и простить поправить.

Лично для меня эти наблюдения были интересны:
1. Для подсчёта суммы ряда в FP достаточно складывать его элементы с конца. Как ни странно это обеспечивает достаточную точность (при всех других фокусах FP).

2. Методы повышения точности "пропорцией" -- не работают.
Условно у нас есть ряды: 1/(x+1)^2 < 1/(x*(x+a)) < 1/x^2.
Мы можем, в зависимости от значения "a" сказать -- к какой из границ ближе среднее значение:
- а = 1 -- посредине
- а = 0 -- на верхней границе
- 0 < a < 1 -- пропорция
Этот метод увеличивает точность не более, чем вдвое. Это мало.

3. Если нас интересуют какие-то обычные научно-инженерные рассчёты, с не растущей непредсказуемо ошибкой (т.е. относительная точность < 10^-17, прикидываться должно "за пару минут на обычном процессоре),То для прикидок ( ... )

Reply

Re: Общие соображения №2 (да простит меня автор) ahiin March 29 2018, 09:57:45 UTC
На практике, конечно, желательно степени повыше, и чем выше, тем лучше.
Я покажу завтра, как этого можно добиться в этой задаче.

Reply

Re: Общие соображения №2 (да простит меня автор) ahiin March 29 2018, 10:01:28 UTC
Кстати,
код ваш опубликовать разрешаете?

Reply

Re: Общие соображения №2 (да простит меня автор) son_0f_morning March 29 2018, 10:30:28 UTC
Да конечно.
Мне вообще странны такие вопросы.

ПС
А какая ассимптота в итоговом решении, если не секрет (по-большому счёту интересует это какой-то вариант вложенных сходящихся рядов и скорость схождения там показательная? Или всё-таки 1 раз оценён остаток и что-то степенное)?

Потому, как в кубическом (то, что я назвал "в лоб", а вы "не в лоб" -- с явной квадратичной сходимостью) -- время для 10^-14 странно похоже на ваше 3миллисекунды.

Reply


alexis_m March 29 2018, 09:29:51 UTC
Ну, раз ты значения выложил, то я схалявил на Питоне.

from __future__ import print_function

import math
import timeit

# https://ahiin.livejournal.com/271654.html

N = 1000000

truth = [
1.6449340668482264,
1.5346072449045607,
1.4408788415467229,
1.360082586782444,
1.2895778007910417,
1.2274112777602189,
1.1721051961250153,
1.1225193425357527,
1.0777588727442429,
1.0371109178506583,
0.99999999999999989
]

def f(x):
a = math.pi ** 2 / 6.0
b = 0
for k in xrange(N, 0, -1):
b += 1.0 / (k + x) / k / k

return a - x * b

def calc(i):
p = truth[i]
x = i / 10.0
q = f(x)
print('{:.1f} {:.16f} {:g}'.format(x, q, abs(q - p)))

def main():
t1 = timeit.default_timer()
print(' x ', '{:18}'.format('f(x)'), 'err')
for n in xrange(11):
calc(n)
t2 = timeit.default_timer()

print(t2 - t1, 'sec')

if __name__ == '__main__':
main()

Результат

x f(x) err ( ... )

Reply

ahiin March 29 2018, 09:52:27 UTC
Это ровно то, что надо) Практически дословно мое решение 2002 года, с поправкой на язык.

Reply

ahiin March 29 2018, 09:58:03 UTC
Прикрыл до завтра.

Reply


Leave a comment

Up