Подтвердить что ты не робот

Как эффективно отлаживать spyder в Python?

Мне нравится Python, и мне нравится Spyder, но я считаю, что отладка со Spyder ужасна!

  • Каждый раз, когда я помещаю точку прерывания, мне нужно нажать две кнопки: сначала отладки, а затем кнопки продолжения (она приостанавливается на первой строке автоматически), что раздражает.
  • Более того, вместо того, чтобы иметь стандартную консоль iPython с автозавершением и т.д., у меня есть паршивая консоль ipdb → , которая просто мусор.
  • Хуже всего то, что эта консоль зависает очень часто, даже если я пишу отпечатки или простую оценку, чтобы попытаться выяснить, что такое ошибка. Это намного хуже, чем Matlab.
  • И последнее, но не менее важное: если я вызываю функцию изнутри ipdb → console, и установите в нем точку останова, она не остановится на этом. Кажется, я должен поставить точку останова там, прежде чем я начну отладки (ctrl + F5).

У вас есть решение или, может быть, вы можете сказать мне, как вы отлаживаете скрипты и функции python?

Я использую новую установку Anaconda на 64-битной Windows 8.1.

4b9b3361

Ответ 1

(Spyder dev здесь). Мы знаем, что опыт отладки в Spyder далеко не идеален. То, что мы предлагаем прямо сейчас, очень похоже на стандартный отладчик Python, но мы работаем над улучшением ситуации в нашей следующей крупной версии, чтобы обеспечить что-то ближе к тому, что любой ученый ожидал бы от отладчика (короче говоря, регулярную консоль IPython, которая позволяет вы проверяете и записываете переменные в текущей точке останова).

Теперь о ваших точках:

  • Это правда. Мы думаем улучшить это, чтобы, если пользователь нажимает кнопку "Выполнить", и в текущем файле присутствует точка останова, Spyder переходит в режим отладки и выполняет программу до тех пор, пока не будет выполнена первая точка останова.

  • ipdb - это консоль отладчика IPython. К сожалению, из-за ограничений в архитектуре IPython он очень ограничен (без завершения кода и просмотра истории со стрелками). Кроме того, невозможно запустить произвольный код Python либо в ipdb, либо в обычной консоли pdb. Команды, которые вы можете запустить в ipdb, - это те, которые вы можете прочитать при оценке команды help внутри него.

  • Это потому, что, как я уже сказал, вы не можете оценить произвольный код Python.

  • Вам нужно поместить новые контрольные точки в наш редактор, чтобы они синхронизировались с нашими консолями Python/IPython.

Ответ 2

Отладчик pdb отлично работает с регулярным python. Поэтому в Spyder я просто переключаюсь на консоль python всякий раз, когда хочу отлаживать в интерактивном режиме.

import pdb

def yourfunction():
    # Interesting stuff done here
    pdb.set_trace() 

Хорошее введение для отладки с помощью pdb https://pythonconquerstheuniverse.wordpress.com/category/python-debugger/

Ответ 3

Один незначительный дополнительный пункт 3:

Мне также показалось, что консоль отладки часто замерзала, делала отпечатки, оценивала и т.д., но нажатие кнопки остановки (выход из отладки) обычно возвращало ее обратно в конец стека вызовов, а затем я мог вернуться (" u ') к кадру, который я отлаживал. Стоит попробовать. Это может быть для более поздней версии Spyder (2.3.5.2)

Ответ 4

Вот как я отлаживаю Spyder, чтобы не замерзать IDE. Я делаю это, если я изменяю script в режиме отладки.

  • Я закрываю текущую консоль IPython (отладки) [x]
  • Откройте новый [Панель меню- > Консоли- > Откройте консоль IPython]
  • Вновь введите режим отладки [кнопка паузы синего воспроизведения].

Все еще немного раздражает, но у него есть дополнительное преимущество для сброса (сброса) списка переменных.

Ответ 5

Рабочий процесс отладки

Вы должны понимать, что на самом деле вы используете разную интеграцию отладчик Python pdb и ipdb (который использует pdb и к которому можно получить доступ с помощью модуля ipdb). Надеюсь, этот тривиальный пример поможет вам лучше использовать его.

Предположим, вы хотите отладить этот код:

def Waiting_fun():                      #1 line number one
    for i in range(100):                #2
        pass                            #3
                                        #4 
def New_sum(lista, to_s = False):       #5
    result = 0                          #6
    print 1                             #7
    for i in lista:                     #8
        print "summed"                  #9   
        result +=i                      #10
    Waiting_fun()                       #11
    if to_s:                            #12
        result = str(result)
    return result
a = New_sum([1,4,5,7,8])
b = New_sum([1,4],1)
c = 456
d = New_sum([6,8,9],1)
final_result = a*b*c*d
Out: Type error

Быстрая первая отладка с использованием iPython% debug

%debug

Первое, что я делаю, это вызвать pdb из iPython с помощью волшебной команды %debug, вы можете установить ее как механизм по умолчанию с помощью %pdb.

%debug
> /home/opdate/Desktop/test.py(23)<module>()
     19 a = New_sum([1,4,5,7,8])
     20 b = New_sum([1,4],1)
     21 c = 456
     22 d = New_sum([6,8,9],1)
---> 23 final_result = a*b*c*d

После обеда pdb. Вы можете найти всю команду в официальных документах или вы можете использовать команду h для их отображения. На этом этапе единственными командами, которые я использую, являются:

  • p: печатает указанные вами переменные
  • pp: красивые отпечатки
  • args: если вы находитесь внутри функции, она печатает аргументы
  • pp locals(): может быть полезно распечатать все переменные, но большая часть времена это беспорядок!
  • ! используйте его, если вы хотите избежать конфликтов с командами, перечисленными в h
  • whatis имя_переменной: эквивалент типа (variable_name)
  • u: переместите текущий кадр на один уровень вверх в трассировке стека (на более старый фрейм).
  • d: переместите текущий кадр на один уровень вниз в трассировке стека (в новый кадр).
  • q: когда вы закончите, вы можете использовать q для выхода из

В нашем случае:

ipdb> pp a,b,c,d
(25, '5', 456, '23')

Или ipdb> !a,b,c,d (нет пробела между значком esclamation и первым значением). Ясно, что b и d являются строками в случае, если мы можем использовать:

ipdb> whatis b
<type 'str'>

Более глубокое использование точек останова

70% времени %debug указывает на решение. Когда вам нужно больше функций, таких как точки останова, пришло время использовать Spyder. В этом случае мы хотим понять, почему b является строкой, которую мы помещаем рядом с ней. Я считаю намного лучше использовать стандартную консоль Python вместо консоли IPython для отладки, поэтому выберите консоль перед началом отладки: введите описание изображения здесь

Затем откройте variable explorer, если есть какие-либо переменные, удаляющие их. Я использую Ctrl + F5, чтобы начать отладку, вы можете использовать кнопки сверху, но я предпочитаю использовать их ярлыки, показанные ниже:

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

(Pdb) c # we go to the breakpoint 
(Pdb) s # we step into the function
(Pdb) args # we see what parameters are inserted
(Pdb) s # going step-by-step
(Pdb) ⏎ # series of Enters go line by line quicker
#Here I'll use  whatis command but in fact I just look to
# the type in variable explorer of spyder.
(Pdb) whatis result #check if result is still int
(Pdb) unt #or until -useful to exiting from loops see doc.
(Pdb) n # we  don't  enter to the Waiting_fun function
(Pdb) s # going step-by-step
(Pdb) whatis result #we find that there the int is converted
(Pdb) j 6 # for double checking we jump back to 6 were the result is assigned 
# We may be tempted to j(ump) to line 12 but doing so we would skip all the code
#for avoiding a series of `s`,`unt` and `n` we can use this solution:
(Pdb) tbreak 12 #set a new temporary breakpoint. Also `b` it ok most of the time
(Pdb) c  # go to it 
(Pdb) j 6 # we jump to 6 the code we jump is NOT executed
(Pdb) whatis result# we find that if we jump 12-13 result is still int

Теперь мы обнаружили ошибку. Мы также можем проверить решение, мы повторяем шаг до 12 и устанавливаем to_s = False

(Pdb) to_s = False #!to_s = False to be on the safe side

Это работает. Одна важная функция, использующая стандартный pdb в консоли Python, заключается в том, что у вас есть автоматическая конкуренция, и вы можете использовать проводник переменных вместо использования whatis и pp:

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

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

Условные точки останова

Еще один более удобный способ найти ошибку - использовать условную точку останова (Shift + F12), большое преимущество Spyder заключается в отладке и использовании контрольных точек списка. Условные точки останова активируются, когда условие True В нашем случае мы хотим найти, где b становится строкой, поэтому условие: type(b) == str. Я обычно размещаю много условных точек останова и вижу, какой из них соответствует условию. Для этого не используйте Shift + F12, но поместите обычные точки останова, дважды щелкнув рядом с линией, и перейдите к точкам останова Debug- > List и скопируйте и минуйте условие в таблице на каждую точку останова, как показано на рисунке ниже.

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

Здесь используются следующие команды:

(Pdb) c  # go to the first
(Pdb) u # it helps to understand when it happened
(Pdb) d # come back to the breakpoint