2013-09-25 7 views
0

Я понимаю, что здесь происходит, мне просто нужны советы о том, как поймать мою программу, прежде чем он войдет в бесконечный цикл. Вот мой код:Хотя бесконечный цикл python

while abs(error) > 50: 
    if Co > To: 
     c = c + 0.1 
    else: 
     c = c - 0.1 

    ##Here I recalculate Co, the function is Co = 1/b type curve 
    ##Here I recalculate To, the function is To = e^b type curve 

    error = Co - To 

Проблема в том, что в зависимости от проблемы, мне иногда нужно быть более точным (я должен был бы изменить итерации строку с + 0,00001, например), поскольку ошибка скачки от значения ниже 50 до значения более 50 на каждом цикле. Как я могу поймать такой бесконечный цикл.

+3

Исправьте вступающих. – Hamish

+1

Основываясь на отступе кода, который вы показываете нам, значение 'error' НЕ изменяется внутри цикла while. Вы имели в виду подпункт 'error = C - T' еще четыре пробела справа? –

+1

Исправлено, что намереваясь – user2817017

ответ

2

Я думаю, что это вопрос конвергенции. В наши дни моя математика foo терпит неудачу, но если вы беспокоитесь, что можете оказаться в положении, когда вы можете не сходиться, вы можете просто добавить счетчик к вашему циклу.

limit = 1000 
while abs(error) > 50: 
    limit -= 1 
    if limit == 0: 
     raise SomeError 
    your_calcs 

Это немного жестокий, но по крайней мере он решает проблему его висит. Звучит так, как будто вы не можете гарантировать, что этот цикл когда-либо закончится из-за характера изменяющегося кода/данных. Если бы эта ситуация с бесконечным контуром произошла, я бы хотел увидеть ошибку, чтобы я мог ее изучить. На самом деле зависит от вашей проблемной области.

+0

Нет необходимости в круглых скобках после 'SomeError '. Вы ставите их только в том случае, если вы сообщаете об ошибке. В противном случае 'raise SomeError' будет работать нормально. – iCodez

+0

Обновлено. Спасибо @iCodez –

+0

Совсем не зверски. Это решение для той же проблемы, когда оно было первоначально поднято в 1960-х годах. Иногда система функций не сходится. Должен вытащить вилку в какой-то момент. –

0

Если я понимаю, о чем вы спрашиваете, я думаю, что вы ищете какую-то адаптивную скорость обучения, как вы могли бы видеть применительно к методу спуска градиента в ANN, а также способ остановить, если что-то происходит больше не улучшается.

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

например,

lR = 1.0 
updatedLR = False # Have we updated the learning rate this iteration? 
while abs(error) > 50 and (sigErrChange or updatedLR): 
    sigErrChange = False # Has there been a significant improvement in the error? (Probably shouldn't just use a single iteration for this...) 

    # Are we adding or subtracting 
    if C > T: 
     sign = 1. 
    else: 
     sign = -1. 

    # Should we update the learning rate? 
    if (~sigErrChange) 
     updatedLR = True 
     lR = .95 * lR 

    # Calculate our values 
    c = c + sign*lR*.001 

    C = calcC(c, C, T) 
    T = calcT(c, C, T) 

    error = C - T 
Смежные вопросы