The print used to be a statement in Python 2, but now it became a function that requires parenthesis in Python 3.
Is there anyway to suppress these parenthesis in Python 3? Maybe by re-defining the print function?
So, instead of
print ("Hello stack over flowers")
I could type:
print "Hello stack over flowers"
Although you need a pair of parentheses to print in Python 3, you no longer need a space after print, because it's a function. So that's only a single extra character.
If you still find typing a single pair of parentheses to be "unnecessarily time-consuming," you can do p = print and save a few characters that way. Because you can bind new references to functions but not to keywords, you can only do this print shortcut in Python 3.
Python 2:
>>> p = print
File "<stdin>", line 1
p = print
^
SyntaxError: invalid syntax
Python 3:
>>> p = print
>>> p('hello')
hello
It'll make your code less readable, but you'll save those few characters every time you print something.
Using print without parentheses in Python 3 code is not a good idea. Nor is creating aliases, etc. If that's a deal breaker, use Python 2.
However, print without parentheses might be useful in the interactive shell. It's not really a matter of reducing the number of characters, but rather avoiding the need to press Shift twice every time you want to print something while you're debugging. IPython lets you call functions without using parentheses if you start the line with a slash:
Python 3.6.6 (default, Jun 28 2018, 05:43:53)
Type 'copyright', 'credits' or 'license' for more information
IPython 6.4.0 -- An enhanced Interactive Python. Type '?' for help.
In [1]: var = 'Hello world'
In [2]: /print var
Hello world
And if you turn on autocall, you won't even need to type the slash:
In [3]: %autocall
Automatic calling is: Smart
In [4]: print var
------> print(var)
Hello world
Use Autohotkey to make a macro. AHK is free and dead simple to install. www.autohotkey.com
You could assign the macro to, say, alt-p:
!p::send print(){Left}
That will make alt-p put out print() and move your cursor to inside the parens.
Or, even better, to directly solve your problem, you define an autoreplace and limit its scope to when the open file has the .py extension:
#IfWinActive .py ;;; scope limiter
:b*:print ::print(){Left} ;;; I forget what b* does. The rest should be clear
#IfWinActive ;;; remove the scope limitation
This is a guaranteed, painless, transparent solution.
No. That will always be a syntax error in Python 3. Consider using 2to3 to translate your code to Python 3
The AHK script is a great idea. Just for those interested I needed to change it a little bit to work for me:
SetTitleMatchMode,2 ;;; allows for a partial search
#IfWinActive, .py ;;; scope limiter to only python files
:b*:print ::print(){Left} ;;; I forget what b* does
#IfWinActive ;;; remove the scope limitation
I finally figured out the regex to change these all in old Python2 example scripts. Otherwise use 2to3.py.
Try it out on Regexr.com, doesn't work in NP++(?):
find: (?<=print)( ')(.*)(')
replace: ('$2')
for variables:
(?<=print)( )(.*)(\n)
('$2')\n
for label and variable:
(?<=print)( ')(.*)(',)(.*)(\n)
('$2',$4)\n
You can use operator oveloading:
class Print:
def __lt__(self, thing):
print(thing)
p = Print()
p < 'hello' # -> hello
Or if you like use << like in c++ iostreams.
You can't, because the only way you could do it without parentheses is having it be a keyword, like in Python 2. You can't manually define a keyword, so no.
In Python 3, print is a function, whereas it used to be a statement in previous versions. As #holdenweb suggested, use 2to3 to translate your code.
I have configured vim to auto-add the parens around my debug def calls when I write the file. I use a simple watcher that auto-runs my updates when the timestamp changes. And I defined CTRL+p to delete them all. The only caveat is that I have to have them alone on a line, which I pretty much always do. I thought about trying to save and restore my previous search-highlight. And I did find a solution on Stack. But it looked a little too deep for now. Now I can finally get back to debugging Ruby-style with a quick p<space><obj>.
function! PyAddParensToDebugs()
execute "normal! mZ"
execute "%s/^\\(\\s*\\)\\(p\\|pe\\|pm\\|pp\\|e\\|ppe\\)\\( \\(.*\\)\\)\\{-}$/\\1\\2(\\4)/"
execute "normal! `Z"
endfunction
autocmd BufWrite *.py silent! call PyAddParensToDebugs()
map <c-p> :g/^\\s*\\(p\\\|pe\\\|pm\\\|pp\\\|e\\\|ppe\\)\\( \\\|\(\\)/d<cr>
I use these Python defs to do my debug printing.
def e():
exit()
def pp(obj):
pprint.PrettyPrinter(indent=4).pprint(obj)
def ppe(obj):
pprint.PrettyPrinter(indent=4).pprint(obj)
exit()
def p(obj):
print(repr(obj))
def pe(obj):
print(repr(obj))
exit()
def pm():
print("xxx")
Related
I haven't been able to figure out what the >>> does, even though I often see it often in source code.
You won't see it in source code, it's probably documentation. It indicates an interactive session, and things typed into the 'interpreter' are marked with this. Output is shown without the arrows.
In fact, the python documentation often has a button >>>at the top right of example code to be able to hide the arrows (and output) so that you can copy and paste the code.
Shown:
Hidden:
'>>>' is the prompt of the interactive Python interpreter, meaning that the interpreter is ready to get Python statements typed in. It's occuring quite often in examples within the documentation of a Python program, in order to show which commands can be used and what will be the result of giving these commands to the interactive interpreter. For example, in a documentation of the print statement, one could give this example:
>>> print "Hello world."
Hello world.
This would be an actual snippet of a session with the interactive Python interpreter.
An interesting feature in IPython is that it ignores leading >>>, meaning that you can copy and paste code from such documentation without needing to remove the leading >>>:
In [1]: >>> print "Hello world."
Hello world.
(The prompt in IPython is In [n]:, where n is counting the interactive commands issued.)
Here are some of my findings on >>> and consequently ... complementing the previous answers.
You only see >>> when you are running Python in interactive mode prompting/asking the user for the "next command". Technical details here.
>>> and ... are not written in stone. These are stored in sys.ps1 and sys.ps2, and therefore can be changed. Further elaborated here.
>>> import sys
>>> sys.ps1 = "$ "
$
Every standard Python has this prompt unless you compile your own Python after changing >>> and ... to what you (sanely) wish to. Apart from that there seems to be a way to change it for all future interactive sessions by changing /usr/lib/python2.7/code.py but I couldn't find any success with it.
The >>> prompt is the Python interpreter’s way of asking you, “What do you want
me to do next?”, and it is called "chevron" prompt
In case you are trying to figure out how to exit a session, run this:
quit()
I found it to be called ' REPL'
>>> def f(x):
... print x
... f('hello')
File "<stdin>", line 3
f('hello')
^
SyntaxError: invalid syntax
>>>
I'm at the prompt in the Python shell. Why doesn't the above code work?
Enter a blank line after "print x". Generally, the ... prompt indicates that Python expects further input for the current block, in this case the function f.
As pointed out by Iguananaut IPython has superior editing capabilities compared to the standard Python shell, for example tab auto completion.
You need to press enter twice after the last line to get back to a >>> prompt in which case you can enter new expressions.
Also, if you're going to by typing lots of multi-line expressions into the interpreter you should give IPython (now with funding!) a look. It supports much better editing of multi-line statements, and even better still if you use the qtconsole or the notebook.
I find myself adding debugging "print" statements quite often -- stuff like this:
print("a_variable_name: %s" % a_variable_name)
How do you all do that? Am I being neurotic in trying to find a way to optimize this? I may be working on a function and put in a half-dozen or so of those lines, figure out why it's not working, and then cut them out again.
Have you developed an efficient way of doing that?
I'm coding Python in Emacs.
Sometimes a debugger is great, but sometimes using print statements is quicker, and easier to setup and use repeatedly.
This may only be suitable for debugging with CPython (since not all Pythons implement inspect.currentframe and inspect.getouterframes), but I find this useful for cutting down on typing:
In utils_debug.py:
import inspect
def pv(name):
record=inspect.getouterframes(inspect.currentframe())[1]
frame=record[0]
val=eval(name,frame.f_globals,frame.f_locals)
print('{0}: {1}'.format(name, val))
Then in your script.py:
from utils_debug import pv
With this setup, you can replace
print("a_variable_name: %s' % a_variable_name)
with
pv('a_variable_name')
Note that the argument to pv should be the string (variable name, or expression), not the value itself.
To remove these lines using Emacs, you could
C-x ( # start keyboard macro
C-s pv('
C-a
C-k # change this to M-; if you just want to comment out the pv call
C-x ) # end keyboard macro
Then you can call the macro once with C-x e
or a thousand times with C-u 1000 C-x e
Of course, you have to be careful that you do indeed want to remove all lines containing pv(' .
Don't do that. Use a decent debugger instead. The easiest way to do that is to use IPython and either to wait for an exception (the debugger will set off automatically), or to provoke one by running an illegal statement (e.g. 1/0) at the part of the code that you wish to inspect.
I came up with this:
Python string interpolation implementation
I'm just testing it and its proving handy for me while debugging.
It seems vims python sripting is designed to edit buffer and files rather than work nicely with vims registers. You can use some of the vim packages commands to get access to the registers but its not pretty.
My solution for creating a vim function using python that uses a register
is something like this.
function printUnnamedRegister()
python <<EOF
print vim.eval('##')
EOF
endfunction
Setting registers may also be possible using something like
function setUnnamedRegsiter()
python <<EOF
s = "Some \"crazy\" string\nwith interesting characters"
vim.command('let ##="%s"' % myescapefn(s) )
EOF
endfunction
However this feels a bit cumbersome and I'm not sure exactly what myescapefn should be.
So I've never been able to get the setting version to work properly.
So if there's a way to do something more like
function printUnnamedRegister()
python <<EOF
print vim.getRegister('#')
EOF
endfunction
function setUnnamedRegsiter()
python <<EOF
s = "Some \"crazy\" string\nwith interesting characters"
vim.setRegister('#',s)
EOF
endfunction
Or even a nice version of myescapefn I could use then that would be very handy.
UPDATE:
Based on the solution by ZyX I'm using this piece of python
def setRegister(reg, value):
vim.command( "let #%s='%s'" % (reg, value.replace("'","''") ) )
If you use single quotes everything you need is to replace every occurence of single quote with two single quotes.
Something like that:
python import vim, re
python def senclose(str): return "'"+re.sub(re.compile("'"), "''", str)+"'"
python vim.command("let #r="+senclose("string with single 'quotes'"))
Update: this method relies heavily on an (undocumented) feature of the difference between
let abc='string
with newline'
and
execute "let abc='string\nwith newline'"
: while the first fails the second succeeds (and it is not the single example of differences between newline handling in :execute and plain files). On the other hand, eval() is somewhat more expected to handle this since string("string\nwith newline") returns exactly the same thing senclose does, so I write this things now only using vim.eval:
python senclose = lambda str: "'"+str.replace("'", "''")+"'"
python vim.eval("setreg('#r', {0})".format(senclose("string with single 'quotes'")))
I'm writing a game engine using pygame and box2d, and in the character builder, I want to be able to write the code that will be executed on keydown events.
My plan was to have a text editor in the character builder that let you write code similar to:
if key == K_a:
## Move left
pass
elif key == K_d:
## Move right
pass
I will retrieve the contents of the text editor as a string, and I want the code to be run in a method in this method of Character:
def keydown(self, key):
## Run code from text editor
What's the best way to do that?
You can use the eval(string) method to do this.
Definition
eval(code, globals=None, locals=None)
The code is just standard Python code - this means that it still needs to be properly indented.
The globals can have a custom __builtins__ defined, which could be useful for security purposes.
Example
eval("print('Hello')")
Would print hello to the console. You can also specify local and global variables for the code to use:
eval("print('Hello, %s'%name)", {}, {'name':'person-b'})
Security Concerns
Be careful, though. Any user input will be executed. Consider:
eval("import os;os.system('sudo rm -rf /')")
There are a number of ways around that. The easiest is to do something like:
eval("import os;...", {'os':None})
Which will throw an exception, rather than erasing your hard drive. While your program is desktop, this could be a problem if people redistributed scripts, which I imagine is intended.
Strange Example
Here's an example of using eval rather strangely:
def hello() : print('Hello')
def world() : print('world')
CURRENT_MOOD = 'happy'
eval(get_code(), {'contrivedExample':__main__}, {'hi':hello}.update(locals()))
What this does on the eval line is:
Gives the current module another name (it becomes contrivedExample to the script). The consumer can call contrivedExample.hello() now.)
It defines hi as pointing to hello
It combined that dictionary with the list of current globals in the executing module.
FAIL
It turns out (thanks commenters!) that you actually need to use the exec statement. Big oops. The revised examples are as follows:
exec Definition
(This looks familiar!)
Exec is a statement:
exec "code" [in scope]
Where scope is a dictionary of both local and global variables. If this is not specified, it executes in the current scope.
The code is just standard Python code - this means that it still needs to be properly indented.
exec Example
exec "print('hello')"
Would print hello to the console. You can also specify local and global variables for the code to use:
eval "print('hello, '+name)" in {'name':'person-b'}
exec Security Concerns
Be careful, though. Any user input will be executed. Consider:
exec "import os;os.system('sudo rm -rf /')"
Print Statement
As also noted by commenters, print is a statement in all versions of Python prior to 3.0. In 2.6, the behaviour can be changed by typing from __future__ import print_statement. Otherwise, use:
print "hello"
Instead of :
print("hello")
As others have pointed out, you can load the text into a string and use exec "codestring". If contained in a file already, using execfile will avoid having to load it.
One performance note: You should avoid execing the code multiple times, as parsing and compiling the python source is a slow process. ie. don't have:
def keydown(self, key):
exec user_code
You can improve this a little by compiling the source into a code object (with compile() and exec that, or better, by constructing a function that you keep around, and only build once. Either require the user to write "def my_handler(args...)", or prepend it yourself, and do something like:
user_source = "def user_func(args):\n" + '\n'.join(" "+line for line in user_source.splitlines())
d={}
exec user_source in d
user_func = d['user_func']
Then later:
if key == K_a:
user_func(args)
You can use eval()
eval or exec. You should definitely read Python library reference before programming.