Is it possible to run code line by line with Python.
Including running any module code, when used, line by line as well.
I would like to go out and run some code line by line and watch as each of the lines goes through the processing phase and see just what code is getting executed when certain actions occur. I'm curious how certain values are getting passed off to the interpreter.
Just use python -m pdb mycode.py, which will run your code in the python debugger (pdb module).
In the debugger you can execute arbitrary code, watch variables, and jump to different places in the code. Specifically, n will execute the next line and h will show you the debugger help.
To add a breakpoint you can use pdb inline:
import pdb; pdb.set_trace()
From this line bleow you can go step by step and you can enter inside every called function (with s) or jump function execution (with n).
Also, a good tip is to use ipdb instead of pdb because it knows autocomplete (it's an ipython prompt)
Related
In trying to solve some errors I am having I would like VS Code debugger to hold my hand and take from module to module, line by line so I can see how the code works. This works as expected if I create two .py files and have code from one call a function from the other.
So if I have one file have the code:
def printer(text):
print(text)
and the second one just say:
from first_file import printer
printer('Hello')
when I put a break point on line printer('Hello') of the second file then, when the code stops there, I press F11, it will open the 1st file and I can continue pressing F11 to go on line by line.
This does not seem to happen with my current code which uses a parameter tuner from scikit-learn, namely GridSearchCV. If I put a break point on the line of code which calls the .fit method for this tuner, when the code pauses there and I press F11 it will just carry on and not walk me through the scikit-learn jungle.
Is there a way to make this happen? Some obscure setting that my googling has not revealed?
Could you try to add "justMyCode": false in the launch.json file? like this:
Otherwise, the debugger will only walk through the codes written by the user.
I have a validator function as part of a bigger program which is fifty lines long which returns True or False when you give it a string. For a certain string, it is currently returning False, and I don't which of the many return statements is firing. I can open the Python Console of the interpreter and import the function then give it its argument, but not see on which line it is returning False. Would rather not alter the main program to feed it its argument, would also rather not set breakpoints in the program for this. Is it possible in PyCharm to isolate a function, give it your own custom argument and then step through it line by line?
Am using PyCharm version 2018.2.4
Is it possible in PyCharm to isolate a function, give it your own custom argument and then step through it line by line?
No, it's not unless you create another file and write something like tests there
By clicking on left side of each line you can declare a breakpoint on the line like this:
Then you can go to debug tool window and click on the green play button
More about debuging using PyCharm
Also you can use python's breakpoint()
It is added as a built-in function in Python 3.7 but u can import it to your file on Python's 3.7-
I'm calling a MATLAB script from python using
ml = matlab.engine.start_matlab()
output = ml.myMATLABscript(input1, input2)
The script runs fine in MATLAB, but when I call it from Python it runs into int vs double issues. So far I've been fixing this by interpreting the error message when the script crashes, but it would be nice to see what's going on specifically. For this purpose, I'd like to be able to step through the MATLAB code line for line, even though I've called it from Python.
Turns out this is easier than I expected. Simply programatically set a breakpoint in the MATLAB script. For example:
dbstop if error
Then call the script from Python as before. The MATLAB editor will open in debug mode at the specified breakpoint.
This is also possible without editting the MATLAB script. In that case you need to set the MATLAB breakpoint from Python, using the enginge's eval:
ml = matlab.engine.start_matlab()
ml.eval(dbstop in myMATLABscript if error)
output = ml.myMATLABscript(input1, input2)
For completeness, from MATLAB's documentation:
dbstop in file sets a breakpoint at the first executable line in file.
dbstop in file at location sets a breakpoint at the specified location
dbstop in file if expression sets a conditional breakpoint at the first executable line of the file
dbstop in file at location if expression sets a conditional breakpoint at the specified location.
In a linux terminal typing
python script.py
Will run run script.py and exit the python console, but what if I just want to run a part of the script and leave the console open? For example, run script.py until line 15 and leave the console open for further scripting. How would I do this?
Let's say it's possible, then with the console still open and script.py run until line 15, can I then from inside the console call line fragments from other py files?
...something like
python script.py 15 #(opens script and runs lines 1-15 and leaves console open)
Then having the console open, I would like to run lines 25-42 from anotherscript.py
>15 lines of python code run from script.py
> run('anotherscript.py', lines = 25-42)
> print "I'm so happy the console is still open so I can script some more")
I'm so happy the console is still open so I can script some more
>
Your best bet might be pdb, the Python debugger. You can start you script under pdb, set a breakpoint on line 15, and then run your script.
python -m pdb script.py
b 15 # <-- Set breakpoint on line 15
c # "continue" -> run your program
# will break on line 15
You can then inspect your variables and call functions. Since Python 3.2, you can also use the interact command inside pdb to get a regular Python shell at the current execution point!
If that fits your bill and you also like IPython, you can check out IPdb, which is a bit nicer than normal pdb, and drops you into an IPython shell with interact.
if you want to run script.py from line a to line b, simply use this bash snippet:
cat script.py|head -{a+b}|tail -{b-a}|python -i
replace {a+b} and {b-a} with their values
You could use the python -i option to leave the console open at the end of the script.
It lets your script run until it exits, and you can then examine variables, call any function and any Python code, including importing and using other modules.
Of course your script needs to exit first, either at the end or, if your goal is to debug that part of the script, you could add a sys.exit() or os._exit() call where you want it to stop (such as your line 15).
For instance:
import os
print "Script starting"
a=1
def f(x):
return x
print "Exiting on line 8"
os._exit(0) # to avoid the standard SystemExit exception
print "Code continuing"
Usage example:
python -i test_exit.py
Scrit starting
Exiting on line 8
>>> print a
1
>>> f(4)
4
>>>
You cannot do that directly but you can do something similar from inside Python console (or IDLE) with exec :
just open you favorite Python console
load wanted lines into a string and exec them :
script = 'script.py'
txt = ''
with open(script) as sc:
for i, line in enumerate(sc):
if i >= begline and i<= endline:
txt = txt + line
exec(txt)
You can even write your own partial script runner based on that code ...
EDIT
I must admit that above answer alone really deserved to be downvoted. It is technically correct and probably the one that most closely meet what you asked for. But I should have warned you that it is bad pratice. Relying on line numbers to load pieces of source files is error prone and you should avoid it unless you really know what you are doing and why you do it that way. Python debugger at least allows you to control what are the lines you are about to execute.
If you really have to use this solution be sure to always print and double check the lines that you are about to execute. IMHO it is always both simpler and safer to copy and past lines in an IDE like IDLE that is packaged into any standard Python installation.
I'd like to save the commands for a breakpoint in a .pdbrc, something like:
b 81
commands 1
pp foo.attr1
pp foo.attr2
end
b 108
commands 2
pp bar.attr1
pp bar.attr2
end
This would automate setting the environment for the debugging session. However, this does not work with python -m pdb script.py, because at the line commands 1, the pdb prompt starts and asks me for the commands for the first breakpoint, ignoring what I wrote in .pdbrc; further, it raises a NameError after I type end at the pdb prompt, because of foo.attr1, foo.attr2 and even end. The same happens for the rest of the breakpoints, so I end up with them set but not their commands.
What would be the correct way to do this? Is it even possible?
You probably don't want this set every time you use pdb anywhere. My recommendation would be to set up an alias, such as:
alias setup_myproj b 81;; commands 1;; pp foo.attr1;; pp foo.attr2;; end
Then you can run setup_myproj when appropriate.
My first thought was that the command must be defined on one line:
commands 1;; pp foo.attr1;; pp foo.attr2;; end;;
However, it appears that this will only work at the prompt, and you will incorrectly get:
Usage : commands [bnum]
...
end
if you place the line above in a .pdbrc
Looking at pdb.py it appears that the author does not properly handle defining commands in a pdbrc.
I personally would just temporarily place the print lines in the code I was debugging while using pdbrc to save the breakpoints of interest to get around this.
More than ten years later, but, unfortunately, it looks like pdb still does not properly handle the end command when reading commands from a .pdbrc file. There's now a related issue for cpython.
In the meantime, for simple control flows, it may be possible to work around the issue, simply by not using the commands command. For example, you could do:
# set the breakpoints
b 81
b 108
# continue to the first breakpoint
continue
# execute commands at first breakpoint
pp foo.attr1
pp foo.attr2
# continue to the second breakpoint
continue
# execute commands at second breakpoint
pp bar.attr1
pp bar.attr2
...
Obviously this only works in simple cases where you know which breakpoint will be reached next.