Уведомления

Группа в Telegram: @pythonsu

#1 Янв. 24, 2017 14:38:25

Fanago
Зарегистрирован: 2017-01-24
Сообщения: 2
Репутация: +  0  -
Профиль   Отправить e-mail  

Ошибка в коде

При любом икс выдает единицу

 import math
def f(x):
    s1, s2 = 0, 1
    n = 0
    s = 0
    eps = 0.0001
    while abs(s2 - s1) >= eps:
        s += s2
        s1 = s2
        s2 = ((-1)**n)*x**(2*n)/math.factorial(2*n)
        n += 1
        return s

Отредактировано Fanago (Янв. 24, 2017 14:38:45)

Офлайн

#2 Янв. 24, 2017 14:45:51

py.user.next
От:
Зарегистрирован: 2010-04-29
Сообщения: 9894
Репутация: +  854  -
Профиль   Отправить e-mail  

Ошибка в коде

Все эти задачи делаются без факториалов, потому что факториал сильно замедляет вычисления. Читай про рекуррентные соотношения.



Офлайн

#3 Янв. 24, 2017 14:57:18

FishHook
От:
Зарегистрирован: 2011-01-08
Сообщения: 8312
Репутация: +  568  -
Профиль   Отправить e-mail  

Ошибка в коде

py.user.next
факториал сильно замедляет вычисления.
А если факториал заранее посчитан для нужного диапазона?



Офлайн

#4 Янв. 24, 2017 15:00:40

py.user.next
От:
Зарегистрирован: 2010-04-29
Сообщения: 9894
Репутация: +  854  -
Профиль   Отправить e-mail  

Ошибка в коде

FishHook
А если факториал заранее посчитан для нужного диапазона?
Этот ряд - бесконечный, но даже если ты посчитал что-то там, оно всё равно будет медленным, потому что факториальные числа много весят (больше, чем нужно для рекуррентных соотношений). Для факториальных чисел нужна длинная арифметика, а для длинной арифметики нужны свои операции со всей длинной хренью. А для рекуррентных соотношений нужно короткое число и обычные (быстрые) операции с коротким числом.

Короче, вот эта хрень, которую он предложил - ну, тупо в лоб факториал вычислять на каждом шаге - это обычно в универах не принимают за правильный ответ. А демонстрируют это путём подачи каких-нибудь больших значений, чтобы комп повис на глазах студента и наглядно продемонстрировал ему это.



Отредактировано py.user.next (Янв. 24, 2017 15:06:20)

Офлайн

#5 Янв. 24, 2017 15:13:16

FishHook
От:
Зарегистрирован: 2011-01-08
Сообщения: 8312
Репутация: +  568  -
Профиль   Отправить e-mail  

Ошибка в коде

py.user.next
Короче, вот эта хрень, которую он предложил - ну, тупо в лоб факториал вычислять на каждом шаге - это обычно в универах не принимают за правильный ответ
Если я заранее знаю, что аргумент факториала по заданию не превысит десяти, то демостратор будет неправ.



Офлайн

#6 Янв. 24, 2017 19:00:36

Romissevd
От: Счастье
Зарегистрирован: 2015-03-01
Сообщения: 533
Репутация: +  76  -
Профиль   Отправить e-mail  

Ошибка в коде

Fanago
При любом икс выдает единицу
Так Вы заведомо делаете выражение:
 s2 = ((-1)**n)*x**(2*n)/math.factorial(2*n)
равное 1 при любом х. А выполнение цикла прекратиться сразу же после первого прогона, т.к. return вызываете из цикла
Плюс s2=1, s1=1.

Отредактировано Romissevd (Янв. 24, 2017 19:01:27)

Офлайн

#7 Янв. 25, 2017 03:44:31

py.user.next
От:
Зарегистрирован: 2010-04-29
Сообщения: 9894
Репутация: +  854  -
Профиль   Отправить e-mail  

Ошибка в коде

FishHook
Если я заранее знаю, что аргумент факториала по заданию не превысит десяти, то демостратор будет неправ.
Это нужно просто взять и конкретно замерить: рекуррентное отношение vs. кешированные факториалы.

Но даже если они у тебя закешированы, то при приемлемых значениях n (а там большие значения, иначе точность суммы будет сильно расплывчатой) они у тебя всё равно будут хранится в длинной арифметике.

(Я бы щас проверил и короткие факториалы, и длинные, да надо идти учиться. Вчера вот узнал, что any() и all() в питоне неполные. На самом деле эти функции обычно предикат ещё принимают.
1> lists:any(fun(X) -> X > 3 end, [1,2,3,4,5]).
true
2> lists:any(fun(X) -> X > 3 end, [1,2,3]).
false
3>
так что есть ещё что нового узнать.)



Отредактировано py.user.next (Янв. 25, 2017 03:45:22)

Офлайн

#8 Янв. 25, 2017 05:47:48

FishHook
От:
Зарегистрирован: 2011-01-08
Сообщения: 8312
Репутация: +  568  -
Профиль   Отправить e-mail  

Ошибка в коде

static const unsigned long SmallFactorials[] = {
1, 1, 2, 6, 24, 120, 720, 5040, 40320,
362880, 3628800, 39916800, 479001600,
#if SIZEOF_LONG >= 8
6227020800, 87178291200, 1307674368000,
20922789888000, 355687428096000, 6402373705728000,
121645100408832000, 2432902008176640000
#endif
};

Где здесь длинная арифметика?



Офлайн

#9 Янв. 25, 2017 10:09:12

py.user.next
От:
Зарегистрирован: 2010-04-29
Сообщения: 9894
Репутация: +  854  -
Профиль   Отправить e-mail  

Ошибка в коде

FishHook
Где здесь длинная арифметика?
А где здесь 100! ? Хотя 100 это ещё маленькое число n при n -> +inf

  
>>> math.factorial(100)
93326215443944152681699238856266700490715968264381621468592963895217599993229915608941463976156518286253697920827223758251185210916864000000000000000000000000
>>>

Вот и представь, что подадут 1000 в качестве n (не по эпсилону будут останавливать вычисление суммы, а по количеству членов). И когда надо будет делить на 100! или 1000! предсталяешь операцию деления? В длинной арифметике из основных операций операция деления - самая сложная (много действий там всяких).

Да и ещё тут прикол есть
  
>>> 12345 / math.factorial(100)
1.322779450690889e-154
>>> 12345 / math.factorial(1000)
0.0
>>>
Происходит потеря точности, потому что он очень малое не может представить в виде числа с плавающей точкой, так как оно настолько маленькое, что становится компьютерным нулём, хотя математически нулю не равно.

Так что “знаешь, Вовка, не нужны тебе такие факториалы”
https://www.youtube.com/watch?v=g4Pq4phAzoo



Отредактировано py.user.next (Янв. 25, 2017 10:11:53)

Офлайн

#10 Янв. 25, 2017 10:26:07

FishHook
От:
Зарегистрирован: 2011-01-08
Сообщения: 8312
Репутация: +  568  -
Профиль   Отправить e-mail  

Ошибка в коде

FishHook
Если я заранее знаю, что аргумент факториала по заданию не превысит десяти
py.user.next
А где здесь 100!



Офлайн

Board footer

Модераторировать

Powered by DjangoBB

Lo-Fi Version