Here's a little oddity with 'print' being a reserved word... class thing:
pass
something = thing() something.print = 3
SyntaxError: invalid syntax print something.__dict__
{} something.__dict__['print'] = 3 print something.__dict__
{'print': 3} print something.print
SyntaxError: invalid syntax
See that I can't set the something.print attribute directly, but can
set it indirectly. Is this behaviour 'necessary' or just an anomaly of
the way IDLE detects Syntax Errors ?
Regards,
Fuzzy http://www.voidspace.org.uk/atlantib...thonutils.html 12 2338
Michael Foord wrote: something.__dict__['print'] = 3
Or, slightly prettier, use:
setattr(something, 'print', 3)
See that I can't set the something.print attribute directly, but can set it indirectly. Is this behaviour 'necessary' or just an anomaly of the way IDLE detects Syntax Errors ?
No, that is simply how Python works. You can only use the direct syntax to
set attributes whose names are valid Python identifiers, but indirectly you
can use any string at all as the attribute name. It doesn't do any harm and
sometimes it can be extremely useful.
You can do this pretty much anywhere that Pythonn uses a dict internally.
For example you can call functions with arbitrary keyword arguments
provided you use the ** syntax.
Michael Foord wrote: See that I can't set the something.print attribute directly, but can set it indirectly. Is this behaviour 'necessary' or just an anomaly of the way IDLE detects Syntax Errors ?
I'd say checking at runtime whether attribute names are valid costs too much
performance, so it's not done. Another nice example (on the interactive
prompt, this has nothing to do with idle): class X:
.... pass
.... x = X() setattr(x, "!@~%", 42) dir(x)
['!@~%', '__doc__', '__module__']
:-)
Peter
Michael Foord wrote: Here's a little oddity with 'print' being a reserved word...
class thing: pass
something = thing() something.print = 3 SyntaxError: invalid syntax print something.__dict__ {} something.__dict__['print'] = 3 print something.__dict__ {'print': 3} print something.print SyntaxError: invalid syntax
See that I can't set the something.print attribute directly, but can set it indirectly. Is this behaviour 'necessary' or just an anomaly of the way IDLE detects Syntax Errors ?
It's necessary. You will find that keywords (those having a specific
meaning as a language token, such as "def" and "print") can't be used as
attributes. The fact that you can set the attributes by manipulating the
__dict__ directly isn't relevant - you will find you can only access
such attributes indirectly, since any attempt to do so directly will
result in a syntax error no matter how the Python interpreter is invoked.
regards
Steve
Steve Holden <sh*****@holdenweb.com> wrote:
... See that I can't set the something.print attribute directly, but can set it indirectly. Is this behaviour 'necessary' or just an anomaly of the way IDLE detects Syntax Errors ? It's necessary. You will find that keywords (those having a specific meaning as a language token, such as "def" and "print") can't be used as attributes. The fact that you can set the attributes by manipulating the __dict__ directly isn't relevant - you will find you can only access such attributes indirectly, since any attempt to do so directly will result in a syntax error no matter how the Python interpreter is invoked.
I think that, while you're right for CPython, other Python
implementations are allowed to relax this restriction, and Jython does
so systematically. Since Jython regularly accesses attributes on
Java-implemented classes, I guess that forcing Jython users to jump
through hoops to access, say, foo.yield, bar.print, or baz.def, might
reduce usability too badly. Possibly make it completely unusable if you
had to implement an interface using such a name, too...
This kind of thing, however, is also true of CPython whenever it's
accessing "outside" objects through attributes; and for .NET
implementations I believe that CLR compliant languages are not allowed
to forbid certain method names along their interfaces to other
components. I'm not sure how CORBA's standard Python bindings address
the same problem, how it's met in various interfaces to XML-RPC, COM,
SOAP, and other distributed-objects or foreign-objects APIs.
Given how pervasive this problem is, I do recall some ruminations about
allowing arbitrary identifiers in the specific case in which they fall
right after a dot in a compound name. I don't recall that anything ever
came of these ruminations, though.
Alex al*****@yahoo.com (Alex Martelli) writes: This kind of thing, however, is also true of CPython whenever it's accessing "outside" objects through attributes; and for .NET implementations I believe that CLR compliant languages are not allowed to forbid certain method names along their interfaces to other components. I'm not sure how CORBA's standard Python bindings address the same problem, how it's met in various interfaces to XML-RPC, COM, SOAP, and other distributed-objects or foreign-objects APIs.
I'm fairly sure the approach taken by CORBA bindings is the good old
"append an underscore" hack. I don't know what happens if an
interface declares methods called both "print" and "print_", but
giving the author a good kick seems an appropriate response...
Given how pervasive this problem is, I do recall some ruminations about allowing arbitrary identifiers in the specific case in which they fall right after a dot in a compound name. I don't recall that anything ever came of these ruminations, though.
I think the only problem is that noone has done the work yet.
Python's parser isn't the nicest thing ever. Two snippings spring to
mind:
/* This algorithm is from a book written before
the invention of structured programming... */
(Parser/pgen.c from the Python source).
<glyph> It's interesting that people often say "Hey, I'm looking for
something to work on!"
<glyph> then someone else says "Glyph's code needs a little help."
then the original asker says "SWEET MARY MOTHER OF GOD I'M NOT
TOUCHING THAT! I mean, uh, that's too much work or I'm not
good at it. Or something."
(from Twisted.Quotes).
It's not my itch, and I'm not that interested in learning how to
scratch it...
Cheers,
mwh
--
Finding a needle in a haystack is a lot easier if you burn down
the haystack and scan the ashes with a metal detector.
-- the Silicon Valley Tarot (another one nicked from David Rush)
Duncan Booth <du**********@invalid.invalid> wrote in message news:<Xn***************************@127.0.0.1>... Michael Foord wrote:>> something.__dict__['print'] = 3
Or, slightly prettier, use:
setattr(something, 'print', 3)
See that I can't set the something.print attribute directly, but can set it indirectly. Is this behaviour 'necessary' or just an anomaly of the way IDLE detects Syntax Errors ?
No, that is simply how Python works. You can only use the direct syntax to set attributes whose names are valid Python identifiers, but indirectly you can use any string at all as the attribute name. It doesn't do any harm and sometimes it can be extremely useful.
You can do this pretty much anywhere that Pythonn uses a dict internally. For example you can call functions with arbitrary keyword arguments provided you use the ** syntax.
Right - but although 'print' is a reserved word there is no *need* for
object.print to be reserved.. and as Alex has pointed out that could
actually be damned inconvenient..........
Oh well.....
Regards,
Fuzzy http://www.voidspace.org.uk/atlantib...thonutils.html
Michael Foord wrote: Right - but although 'print' is a reserved word there is no *need* for object.print to be reserved.. and as Alex has pointed out that could actually be damned inconvenient..........
I tried to explain my views on that before: http://groups.google.com/groups?hl=e...com%26rnum%3D4
The key issue is, that while def foo(): pass print foo
<function foo at 0x401eab1c>
is ok,
def print(): pass
fails here, but if not print print
can't possibly made working without unclear context-driven hacks.
And if on "normal" function level this can't be allowed, IMHO for the sake
of consistency class methods should also not allow that - because then the
different behaviour causes confusion...
--
Regards,
Diez B. Roggisch
On Wed, 15 Sep 2004 23:09:22 +0200, "Diez B. Roggisch" <de*********@web.de> wrote: Michael Foord wrote: Right - but although 'print' is a reserved word there is no *need* for object.print to be reserved.. and as Alex has pointed out that could actually be damned inconvenient.......... I tried to explain my views on that before:
http://groups.google.com/groups?hl=e...com%26rnum%3D4
The key issue is, that while
def foo(): pass print foo<function foo at 0x401eab1c>
is ok, def print(): passfails here, but if not print print
can't possibly made working without unclear context-driven hacks.
Why? If a print statement were just syntactic sugar for print((outfile,), ... rest, of, line)
(normally calling a builtin) then, giving your example args,
def print(*args):
import sys
sys.stdout.write( repr(args)+'\n')
print print, 1, 'two', 3
would output (faked ;-)
'((), <function print at 0x008FDE70> 1, "two", 3)'
instead of blowing up, and the _statement_
print(print)
would, de-sugared, act like print((), (print)) and thus output
'((), <function print at 0x008FDE70>)'
without the def print(...
print print
would de-sugar to
print((), print)
and output
<built-in function print>
and
type(print)
would not be a print statement, so would return
<type 'builtin_function_or_method'>
interactively.
Etc., etc. And if on "normal" function level this can't be allowed, IMHO for the sake of consistency class methods should also not allow that - because then the different behaviour causes confusion...
Maybe there's a problem with my suggestion, but I don't see it at the moment.
Regards,
Bengt Richter
> Why? If a print statement were just syntactic sugar for print((outfile,), ... rest, of, line) (normally calling a builtin) then, giving your example args,
def print(*args): import sys sys.stdout.write( repr(args)+'\n')
print print, 1, 'two', 3
would output (faked ;-)
'((), <function print at 0x008FDE70> 1, "two", 3)'
How should that happen? As
print
produces a newline, one should expect that
print print
gets translated to
print(outfile, print(outfile,))
which would clearly produce two newlines and raises the question what the
inner print gets evaluated to so that the outer one wouldn't print
anything.
While that would be sort of accetable, what you suggest makes print
ambigious - depending on the context. And above that: len
<built-in function len>
has no sideeffects whatsoever, where
print
clearly has.
As BDFL has already said, he regrets to have introduced print as a statement
- but as he did, there is no really elegant way around having print as a
reserved keyword. One _can_ think of taking context into account to either
interpret print as keyword or as identifier while parsing - the question
is: Is it worth it? IMHO no - but as Alex said: If it makes you happy,
implement it :) The same applies to all other keywords as well, btw.
--
Regards,
Diez B. Roggisch
In article <m3************@pc150.maths.bris.ac.uk>,
Michael Hudson <mw*@python.net> wrote: al*****@yahoo.com (Alex Martelli) writes:
This kind of thing, however, is also true of CPython whenever it's accessing "outside" objects through attributes; and for .NET implementations I believe that CLR compliant languages are not allowed to forbid certain method names along their interfaces to other components. I'm not sure how CORBA's standard Python bindings address the same problem, how it's met in various interfaces to XML-RPC, COM, SOAP, and other distributed-objects or foreign-objects APIs.
I'm fairly sure the approach taken by CORBA bindings is the good old "append an underscore" hack. I don't know what happens if an interface declares methods called both "print" and "print_", but giving the author a good kick seems an appropriate response...
CORBA prepends an underscore, so it would use "_print". Identifiers in
CORBA IDL are not permitted to start with an underscore, so there is
no possibility of a clash with another IDL defined identifier. If the
Python mapping appended an underscore for clashes, it would be
susceptible to the issue you mention.
Cheers,
Duncan.
--
-- Duncan Grisby --
-- du****@grisby.org --
-- http://www.grisby.org --
On Thu, 16 Sep 2004 03:39:05 +0200, "Diez B. Roggisch" <de*********@web.de> wrote: Why? If a print statement were just syntactic sugar for print((outfile,), ... rest, of, line) (normally calling a builtin) then, giving your example args,
def print(*args): import sys sys.stdout.write( repr(args)+'\n')
print print, 1, 'two', 3
would output (faked ;-)
'((), <function print at 0x008FDE70> 1, "two", 3)'
How should that happen? As
print
produces a newline, one should expect that
print print
gets translated to
print(outfile, print(outfile,))
No, the second print in print print is just a name.
The translation is
print((), print)
where after this translation both prints are ordinary names, and the print
statement per se is effectively forgotten as far as compilation is concerned.
That's why it finds <function print at 0x008FDE70> from the def print if there is one,
or otherwise the builtin print _function_. Either way, it's a function found in the
ordinary way by the name print.
The point is, a print statement is recognized _syntactically_ by 'print' being the
first name in the statement, but for the rest of the statement 'print' is an ordinary name.
Thus
print; foo = print; foo((), 'Hi there')
would print a newline, bind foo to the builtin print function, and invoke the latter via foo,
(using () to indicate default outfile). None could also be used to indicate default outfile.
I just picked () as more flexibly adaptable to what I hadn't thought of yet re specifying outfile ;-)
Maybe a keyword arg would be better yet. I.e., as in def print(*args **kw) with
outfile=kw.get('outfile', sys.stdout). But that's an implementation detail.
which would clearly produce two newlines and raises the question what the inner print gets evaluated to so that the outer one wouldn't print anything.
Not applicable. See above for translation explanation. While that would be sort of accetable, what you suggest makes print ambigious - depending on the context. And above that:
No, you have misunderstood (I wasn't clear enough) my suggestion. No ambiguity,
but yes, a print name token as the leading token of a statement is interpreted
specially. You could interpret print(x) differently from print (x) analogously
to 123.__doc__ (illegal) vs 123 .__doc__ which gives you int docs. len<built-in function len> has no sideeffects whatsoever, where print clearly has.
as does
sys.stdout.write('\n')
so I guess I am missing your point. As BDFL has already said, he regrets to have introduced print as a statement - but as he did, there is no really elegant way around having print as a reserved keyword. One _can_ think of taking context into account to either interpret print as keyword or as identifier while parsing - the question is: Is it worth it? IMHO no - but as Alex said: If it makes you happy, implement it :) The same applies to all other keywords as well, btw.
It doesn't seem that complex a context for print, but I haven't thought
about the other keywords yet (no time really for this even ;-/). I wonder
what a comprehensive writeup of python name semantics would reveal,
discussing all the different name spaces and ways that names are searched for
and used in various contexts.
Regards,
Bengt Richter
> No, the second print in print print is just a name. The translation is print((), print) where after this translation both prints are ordinary names, and the print statement per se is effectively forgotten as far as compilation is concerned.
I understood that that was what you _wanted_ it to be - but how do you want
to parse that? It would involve saying "first encounter of print is a
keyword, then an identifier" - that condition is reset after the statement,
so to speak the next line or a semicolon.
That surely is possible, but has to be done _after_ lexcal analysis - which
makes things more complicated as necessary, for a very questionable
benefit.
The point is, a print statement is recognized _syntactically_ by 'print' being the first name in the statement, but for the rest of the statement 'print' is an ordinary name. Thus print; foo = print; foo((), 'Hi there')
How shall that work? Right now, print ; print produces two newlines. Do you
want to alter that behaviour? Do you want to complicate parsing even more
by saying that print on the right side of an expression is the name,
otherwise its executed?
That would be inconsistent - every newby would ask why foo
then isn't evaluated, but yields <funtion foo>, whereas
print
produces a nl.
would print a newline, bind foo to the builtin print function, and invoke the latter via foo, (using () to indicate default outfile). None could also be used to indicate default outfile. I just picked () as more flexibly adaptable to what I hadn't thought of yet re specifying outfile ;-) Maybe a keyword arg would be better yet. I.e., as in def print(*args **kw) with outfile=kw.get('outfile', sys.stdout). But that's an implementation detail.
No, you have misunderstood (I wasn't clear enough) my suggestion. No ambiguity, but yes, a print name token as the leading token of a statement is interpreted specially. You could interpret print(x) differently from print (x) analogously to 123.__doc__ (illegal) vs 123 .__doc__ which gives you int docs.> len<built-in function len>>
has no sideeffects whatsoever, where
> print
>
clearly has. as does
sys.stdout.write('\n')
so I guess I am missing your point.
The point is that two things that look alike should behave the same for
reasons of orthogonality - having as special-case of print here does
produce behaviour that yields to confusion, as I said before. That is of
course also true right now - but because print beeing a reserved keyword,
nobody falls into any traps here - its just forbidden.
It doesn't seem that complex a context for print, but I haven't thought about the other keywords yet (no time really for this even ;-/). I wonder what a comprehensive writeup of python name semantics would reveal, discussing all the different name spaces and ways that names are searched for and used in various contexts.
Well, its certainly more complicated than just altering the lexical phase -
it requrires a post-reduction step - deep in the parser.
--
Regards,
Diez B. Roggisch This thread has been closed and replies have been disabled. Please start a new discussion. Similar topics
by: Natsu Mizutani |
last post by:
Hello,
I'm trying to wrap a c++ library using MPI inside with boost.python
(or SWIG).
I managed to find that calling `MPI::Init()` embeded in a c++ funtion
would not work. So, I decided to use...
|
by: Michele Simionato |
last post by:
So far, I have not installed Prothon, nor I have experience with Io, Self
or other prototype-based languages. Still, from the discussion on the
mailing list, I have got the strong impression that...
|
by: could ildg |
last post by:
I have learned python for over a month.
I heard that it was very easy to learn, but when I tried to know OO of python,
I found it really weird, some expressions seem very hard to understand,
and I...
|
by: rxl124 |
last post by:
Hi, room
Beginner of learning perl here!!
I have question to all,
I have below file name datebook.master which contains only 2 lines
Mike wolf:12/3/44:144 park ave, paramus: 44000
Sarah kim:...
|
by: bruce |
last post by:
hi...
it appears that i'm running into a possible problem with
mechanize/browser/python rgarding the "select_form" method. i've tried the
following and get the error listed:
br.select_form(nr...
|
by: metaperl |
last post by:
-- python -i
File "<stdin>", line 1
class = "algebra"
^
SyntaxError: invalid syntax
Why isn' t the parser smart enough to see that class followed by an
identifier is used for class...
|
by: per9000 |
last post by:
Hi,
I recently started working a lot more in python than I have done in
the past. And I discovered something that totally removed the pretty
pink clouds of beautifulness that had surrounded my...
|
by: WP |
last post by:
Hello, below is my very first python program. I have some questions
regarding it and would like comments in general. I won't be able to get
my hands on a good python book until tomorrow at the...
|
by: isladogs |
last post by:
The next Access Europe meeting will be on Wednesday 4 Oct 2023 starting at 18:00 UK time (6PM UTC+1) and finishing at about 19:15 (7.15PM)
The start time is equivalent to 19:00 (7PM) in Central...
|
by: giovanniandrean |
last post by:
The energy model is structured as follows and uses excel sheets to give input data:
1-Utility.py contains all the functions needed to calculate the variables and other minor things (mentions...
|
by: NeoPa |
last post by:
Hello everyone.
I find myself stuck trying to find the VBA way to get Access to create a PDF of the currently-selected (and open) object (Form or Report).
I know it can be done by selecting :...
|
by: Teri B |
last post by:
Hi, I have created a sub-form Roles. In my course form the user selects the roles assigned to the course.
0ne-to-many. One course many roles.
Then I created a report based on the Course form and...
|
by: nia12 |
last post by:
Hi there,
I am very new to Access so apologies if any of this is obvious/not clear.
I am creating a data collection tool for health care employees to complete. It consists of a number of...
|
by: NeoPa |
last post by:
Introduction
For this article I'll be focusing on the Report (clsReport) class. This simply handles making the calling Form invisible until all of the Reports opened by it have been closed, when it...
|
by: isladogs |
last post by:
The next online meeting of the Access Europe User Group will be on Wednesday 6 Dec 2023 starting at 18:00 UK time (6PM UTC) and finishing at about 19:15 (7.15PM).
In this month's session, Mike...
|
by: GKJR |
last post by:
Does anyone have a recommendation to build a standalone application to replace an Access database? I have my bookkeeping software I developed in Access that I would like to make available to other...
|
by: SueHopson |
last post by:
Hi All,
I'm trying to create a single code (run off a button that calls the Private Sub) for our parts list report that will allow the user to filter by either/both PartVendor and PartType. On...
| |