Re: cause __init__ to return a different class?
On 15/09/11 15:35, Chris Rebert wrote: > On Wed, Sep 14, 2011 at 10:20 PM, Matthew Pounsett > wrote: >> I'm wondering if there's a way in python to cause __init__ to return a class >> other than the one initially specified. My use case is that I'd like to >> have a superclass that's capable of generating an instance of a random >> subclass. > >> Is there a way to do this? > > Override __new__() instead: > http://docs.python.org/reference/datamodel.html#object.__new__ The above will do exactly what you want, but it's generally bad style unless you have a very specific use-case. Is there a particular reason you need to "magically" return a subclass, rather than making this explicit in the code? To be friendlier to others reading your code, I would consider using a classmethod to create an alternative constructor: class MyBaseClass(object): @classmethod def get_random_subclass(cls, *args, **kwds) subcls = random.choice(cls.__subclasses__()) return subcls(*args, **kwds) To me, this reads pretty cleanly and makes it obvious that something unusual is going on: obj = MyBaseClass.get_random_subclass() While this hides the intention of the code and would require additional documentation or comments: obj = MyBaseClass() # note: actually returns a subclass! Just a thought :-) Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: OpenPGP digital signature -- http://mail.python.org/mailman/listinfo/python-list
PyCon Australia 2011: Registration Closing Soon!
Hi Everyone, Registrations for PyCon Australia 2011 are closing soon! The conference is just over a week away, so we need final numbers in the next few days. If you're planning to attend, please register now! PyCon Australia is Australia's only conference dedicated exclusively to the Python programming language, and will be held at the Sydney Masonic Center over the weekend of August 20 and 21. See below for more information and updates on: 1. Registration Closing Soon 2. Coffee 3. Hosting Panel 4. More Sponsors Announced Please pass this message on to those you feel may be interested. Registration Closing Soon = Full Registrations for the conference will be closing on: Monday 15th August: Full Registrations close That's only five days away, so register now to be sure you don't miss out. By request, we will still allow latecomers to register until just before the conference. However, since it's after the deadline for catering and printing, you won't be entitled to a T-shirt or a seat at the conference dinner: Thursday 18th August: Last-Minute Registrations close Please note that we will *not* accept registrations at the door. So don't delay, register now at: http://pycon-au.org/reg Coffee == Thanks to gold sponsors Arclight, we will be able to provide one of the most requested additions to this year's conference: Coffee! Yes, Arclight have generously agreed to provide a free coffee cart for the duration of the conference. And there was much rejoicing. Hosting Panel = Saturday evening will feature an informal panel discussion with several hosting providers. Come and hear from our hosting panel about why their services are right for hosting your next Python project! Each group will give a quick 5 minute spiel, to be followed by a casual drink before the conference dinner. This event is happening in a private area at Mr B's pub, across the street from the SMC. As this is a licensed venue anyone under 18 will have to be accompanied by a parent or guardian. More Sponsors Announced === We are delighted to confirm that the Django Software Foundation and Ninefold have joined as Silver sponsors. In addition, Arclight have upgraded to Gold Sponsorship, Anchor have agreed to sponsor video production, and GitHub will be sponsoring internet access. Thanks once again to the following companies for their continuing support of Python and for helping to make PyCon Australia 2011 a reality: Gold: Google <http://www.google.com.au/> Gold: ComOps <http://www.comops.com.au/> Gold: Arclight <http://www.arclight.com.au/> Video: Anchor<http://anchor.com.au/> Silver: Enthought<http://www.enthought.com/> Silver: Python Software Foundation <http://www.python.org/psf/> Silver: WingWare <http://www.wingware.com/> Silver: Bitbucket by Atlassian <http://bitbucket.org/> Silver: Microsoft<http://www.microsoft.com/> Silver: Django Software Foundation <http://www.djangoproject.com> Silver: Ninefold <http://ninefold.com/> Internet: GitHub <http://github.com/> Thanks also to Linux Australia, who provide the overarching legal and organisational structure for PyCon Australia. Ryan Kelly PyCon Australia 2011 -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details -- http://mail.python.org/mailman/listinfo/python-list
Re: import hooks (PEP 302) broken in Python >=2.5?
On Sun, 2011-08-07 at 11:11 -0700, Josh Haberman wrote: > When reading about import hooks, I came across a blog entry comment > that says: > > One additional thing to note about ihooks is that it's > somewhat seriously broken on Python 2.5 and newer and there > seems to be little or no interest in fixing it. It's > probably worth *always* avoiding when writing new code. > > --http://orestis.gr/blog/2008/12/20/python-import-hooks/#c264 > > Does anyone know what this is referring to? Should I be wary of > relying on import hooks? I believe that comment is referring specifically to "ihooks" the stdlib module, not "import hooks" the general concept as defined in PEP302. The former pre-dates the later. I use custom PEP302 loaders all the time and they work fine in at least 2.6, 2.7 and 3.2. Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Code War at PyCon Au 2011
A huge hit at PyCon-Au last year, Code War is back! Eight teams, onstage knockout rounds of short programming bouts, loud crowd...mildly impressive prizes. Any language allowed, no holds bared. Think of it like cage fighting for coders. Originally based on an idea from the book PeopleWare, CodeWar has been run in conjunction with the Sydney WebDU conference since 2008 with great success. To help share the mayhem we're proud to bring CodeWar to PyCon-au 2011, with experienced CodeWar compare Robin Hilliard from RocketBoots on the microphone to keep a wry eye on proceedings. All comers welcome -- no conference ticket required. Come to compete or just come to watch. RSVP now! If you want to enter a team read on... Tourney Rules - The competition will consist of three rounds: * 8 teams of 3-5 people * 1 laptop per team connected to projector on stage. * Rounds are first-past-the-post simple programming challenges * Any programming language you want. We guarantee this won't be mind twisting problems for algorithm heads. It will help to have a team with a mix of skills, a clever and/or intimidating team name and vocal cheer squad. For example: "Here is the complete text of pride and prejudice on this usb key. Be the first to print out the 7th and 25th sentances that contain both 'Elizabeth'and 'Darcy'". See a list of questions from recent code war events. If you're registering a team, the team leader should get 1 team leader ticket and the team members a RSVP ticket. Don't forget to bring your team and single laptop on the day. If all the team slots are gone register your standby team in case of a no-show. http://codewarpyconau.eventbrite.com/ Thanks to Dylan Jay of PretaWeb for organising CodeWar this year. -- http://mail.python.org/mailman/listinfo/python-list
PyCon Australia 2011: Registration Back Online
Hi Everyone, After a brief hiatus, registrations for PyCon Australia 2011 are back online! We have extended some registration deadlines to compensate for the outage. PyCon Australia is Australia's only conference dedicated exclusively to the Python programming language, and will be held at the Sydney Masonic Center over the weekend of August 20 and 21. See below for more information and updates on: 1. Registration Back Online 2. Call for Volunteers 3. Convore Group 4. Thanks to our Sponsors Please pass this message on to those you feel may be interested. Registration Back Online Registrations are back online after a brief PayPal outage: http://pycon-au.org/reg Our apologies to those inconvenienced. PayPal put a temporary lock on our account while they were reviewing our status as a non-profit. Many thanks to the hard-working folks at Linux Australia for following up with all the necessary paperwork. To compensate for the outage we have adjusted some of our registration deadlines. The new dates are: 1st August: T-Shirt order finalised 8th August: Special dietary needs finalised 15th August: Last chance to get tickets! Remember, registrations must close on Monday the 15th of August, and we will not be accepting registrations at the door. So don't delay, register now at: http://pycon-au.org/reg Call for Volunteers === A community conference such as PyCon just can't run without the work of many generous volunteers. If you're interested in helping out, please send us an email at: pycon-...@pycon-au.org We're currently looking for people to help with the following: * Session Staff (see http://pycon-au.org/2011/helping/session_staff/) * Bag Packers (Friday afternoon; also just general setup of the venue) * Registration Desk Convore Group = We've set up a group on Convore for anyone wanting to chat about the conference: https://convore.com/pycon-au-2011/ There are already some good tips from Sydney-siders who know the area around the venue. If you have any more, please share! Don't forget, you can also follow us on Twitter for the latest updates: https://twitter.com/pyconau https://twitter.com/#!/search/pyconau Thanks to our Sponsors == Thanks once again to the following companies for their continuing support of Python and for helping to make PyCon Australia 2011 a reality: Gold: Google <http://www.google.com.au/> Gold: ComOps <http://www.comops.com.au/> Silver: Anchor<http://anchor.com.au/> Silver: Enthought <http://www.enthought.com/> Silver: Python Software Foundation<http://www.python.org/psf/> Silver: WingWare <http://www.wingware.com/> Silver: Arclight <http://www.arclight.com.au/> Silver: Bitbucket by Atlassian<http://bitbucket.org/> Silver: Microsoft <http://www.microsoft.com/> Thanks also to Linux Australia, who provide the overarching legal and organisational structure for PyCon Australia. Ryan Kelly PyCon Australia 2011 -- http://mail.python.org/mailman/listinfo/python-list
PyCon Australia 2011: Registration Deadlines
Hi Everyone, Registrations for PyCon Australia 2011 are closing soon! The conference is now less than a month away, so we need to start finalising numbers for shirts, catering and the venue itself. If you're planning to attend, please register now so you don't miss out. PyCon Australia is Australia's only conference dedicated exclusively to the Python programming language, and will be held at the Sydney Masonic Center over the weekend of August 20 and 21. See below for more information and updates on: 1. Registration Deadlines 2. More Sponsors Announced Please pass this message on to those you feel may be interested. Registration Deadlines == Registrations for the conference will be closing soon, as we have the following deadlines approaching fast: 29th July:T-Shirt order finalised 8th August: Special dietary needs finalised 15th August: Last chance to get tickets! If you're looking forward to adding a PyCon Au 2011 T-Shirt to your collection, please complete your registration *this week* so we can get one in your size. We will be sending the order through to the printers based on the sizes requested so far. If you have special dietary needs (e.g. vegetarian, vegan, gluten-free) then please complete your registration by Monday the 8th of August. We cannot accommodate special dietary orders submitted after this time. All registrations will close on Monday the 15th of August, so that we can confirm final numbers with the venue and catering. There will be *no* registrations accepted after this date. In particular, we will *not* accept registrations at the door. So don't delay, register now at: http://pycon-au.org/reg More Sponsors Announced === We are delighted to confirm that Microsoft will be joining us this year as a Silver Sponsor. Thanks once again to the following companies for their continuing support of Python and for helping to make PyCon Australia 2011 a reality: Gold: Google <http://www.google.com.au/> Gold: ComOps <http://www.comops.com.au/> Silver: Anchor<http://anchor.com.au/> Silver: Enthought <http://www.enthought.com/> Silver: Python Software Foundation<http://www.python.org/psf/> Silver: WingWare <http://www.wingware.com/> Silver: Arclight <http://www.arclight.com.au/> Silver: Bitbucket by Atlassian<http://bitbucket.org/> Silver: Microsoft <http://www.microsoft.com/> Thanks also to Linux Australia, who provide the overarching legal and organisational structure for PyCon Australia. Ryan Kelly PyCon Australia 2011 -- http://mail.python.org/mailman/listinfo/python-list
Re: Inconsistencies between zipfile and tarfile APIs
On Fri, 2011-07-22 at 01:45 -0400, Terry Reedy wrote: > On 7/22/2011 12:48 AM, rantingrick wrote: > > On Jul 21, 11:13 pm, Corey Richardson wrote: > >> Excerpts from rantingrick's message of Thu Jul 21 23:46:05 -0400 2011: > >> > >>> I may have found the mother of all inconsitency warts when comparing > >>> the zipfile and tarfile modules. Not only are the API's different, but > >>> the entry and exits are differnet AND zipfile/tarfile do not behave > >>> like proper file objects should. > >> > >> I agree, actually. > > Hmm. Archives are more like directories than files. Windows, at least, > seems to partly treat zipfiles as more or less as such. Certainly, 7zip > present a directory interface. So opening a zipfile/tarfile would be > like opening a directory, which we normally do not do. On the other > hand, I am not sure I like python's interface to directories that much. Indeed. Actually, I'd say that archives are more like *entire filesystems* than either files or directories. We have a pretty nice ZipFS implementation as part of the PyFilesystem project: http://packages.python.org/fs/ If anyone cares enough to whip up a TarFS implementation it would be gratefully merged into trunk. (There may even be the start of one in the bugtracker somewhere, I don't recall...) Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
PyCon Australia 2011: Schedule Announced
Hi Everyone, The official schedule for PyCon Australia 2011 has been announced! This year's conference will feature 3 fantastic keynotes, 7 introductory classroom sessions, and 26 presentations on topics as diverse as web programming, benchmarking, social issues and API design. PyCon Australia is Australia's only conference dedicated exclusively to the Python programming language, and will be held at the Sydney Masonic Center over the weekend of August 20 and 21. See below for more information and updates on: 1. Conference Schedule Announced 2. More Sponsors Announced Please pass this message on to those you feel may be interested. Conference Schedule Announced = The detailed conference schedule has been completed and can now be viewed at the following URL: http://pycon-au.org/2011/conference/schedule/ There's even an iCal version for you to plug the schedule straight into your calendar of choice: http://pycon-au.org/2011/conference/schedule/ical/ Thanks again to all our presenters for some outstanding talk proposals this year. Standard Talks: A Python on the Couch (Mark Rees) Behaviour Driven Development (Malcolm Tredinnick) Benchmarking stuff made ridiculously easy (Tennessee Leeuwenburg) Bytecode: What, Why, and How to Hack it (Ryan Kelly) Developing Scientific Software in Python (Duncan Gray) Fun with App Engine 1.5.0 (Greg Darke) Hosting Python Web Applications (Graham Dumpleton) How Python Evolves (and How You Can Help Make It Happen) (Nick Coghlan) Infinite 8-bit Platformer (Chris McCormick) Networking Libraries in Python. (Senthil Kumaran) Pants - Network Programming Made Easy (Evan Davis) Say What You Mean: Meta-Programming a Declarative API (Ryan Kelly) State of CPython and Python Ecosystem (Senthil Kumaran) Sysadmins vs Developers, a take from the other side of the fence (Benjamin Smith) Teaching Python to the young and impressionable (Katie Bell) The NCSS Challenge: teaching programming via automated testing (Tim Dawborn) Weather field warping using Python. (Nathan Faggian) Zookeepr: Home-grown conference management software (Brianna Laugher) In-Depth Talks: Ah! I see you have the machine that goes "BING"! (Graeme Cross) Easy site migration using Diazo and Funnelweb (Adam Terrey) How to maintain big app stacks without losing your mind (Dylan Jay) Introduction to the Geospatial Web with GeoDjango (Javier Candeira) Pyramid: Lighter, faster, better web apps (Dylan Jay) Web micro-framework battle (Richard Jones) Discussion Panels: Panel: Python 3 (Nick Coghlan, Raymond Hettinger, Richard Jones) Panel: Python in the webs (Malcolm Tredinnick, Russell Keith-Magee, Dylan Jay, Richard Jones) Classroom Track: Python 101+ (Peter Lovett) Python's dark corners - the bad bits in Python and how to avoid them (Peter Lovett) Confessions of Joe Developer (Danny Greenfeld) Meta-matters: using decorators for better Python programming (Graeme Cross) Python for Science and Engineering, Part 1 (Edward Schofield) Python for Science and Engineering, Part 2 (Edward Schofield) The Zen of Python (Richard Jones) More Sponsors Announced === We are delighted to announce that Bitbucket by Atlassian has joined us as a Silver Sponsor. Thanks once again to the following companies for their continuing support of Python and for helping to make PyCon Australia 2011 a reality: Gold: Google <http://www.google.com.au/> Gold: ComOps <http://www.comops.com.au/> Silver: Anchor<http://anchor.com.au/> Silver: Enthought <http://www.enthought.com/> Silver: Python Software Foundation<http://www.python.org/psf/> Silver: WingWare <http://www.wingware.com/> Silver: Arclight <http://www.arclight.com.au/> Silver: Bitbucket by Atlassian<http://bitbucket.org/> Thanks also to Linux Australia, who provide the overarching legal and organisational structure for PyCon Australia. Ryan Kelly PyCon Australia 2011 -- http://mail.python.org/mailman/listinfo/python-list
PyCon Australia 2011: Sprints
Hi Everyone, We have confirmed arrangements for two days of Sprints following PyCon Au this year. This will be a great opportunity to contribute to the Python ecosystem under the guidance of experienced developers, so bring your laptops! PyCon Australia is Australia's only conference dedicated exclusively to the Python programming language, and will be held at the Sydney Masonic Center over the weekend of August 20 and 21. See below for more information and updates on: 1. Post-Conference Sprints 2. Thanks to our Sponsors Please pass this message on to those you feel may be interested. Post-Conference Sprints === We are taking up the global PyCon tradition of post-conference sprints this year at PyCon Au. A Sprint is an opportunity for people to get together and do focussed development on a project in a fun and welcoming atmosphere. Experienced developers will be on hand to help newcomers get started, so bring your laptops and take this opportunity to contribute to the Python ecosystem! The sprints will be held on the 22nd and 23rd of August at the Sydney Masonic Center. Sprint leaders and topics so far include: Nick Coghlan: Python core development Audrey Roy/Danny Greenfeld: Django and/or Packaginator Richard Jones: Python Package Index For more information and updates see: http://www.pycon-au.org/2011/sprints/ Please register your interest by emailing pycon-...@pycon-au.org. Thanks to our Sponsors == Thanks once again to the following companies for their continuing support of Python and for helping to make PyCon Australia 2011 a reality: Gold: Google <http://www.google.com.au/> Gold: ComOps <http://www.comops.com.au/> Silver: Anchor<http://anchor.com.au/> Silver: Enthought <http://www.enthought.com/> Silver: Python Software Foundation<http://www.python.org/psf/> Silver: WingWare <http://www.wingware.com/> Silver: Superior Recruitment <http://superiorrecruitment.com.au/> Thanks also to Linux Australia, who provide the overarching legal and organisational structure for PyCon Australia. Ryan Kelly PyCon Australia 2011 -- http://mail.python.org/mailman/listinfo/python-list
Re: doing cross platform file work
On Wed, 2011-06-22 at 10:44 -0700, Tim Hanson wrote: > Thanks for your responses to my student question about using OS paths in > Python. > > For the more general case, I am a Linux user interested in making my scripts > platform neutral, which would include Linux, Unix (including Mac), and > Windows. I have looked at the python.org os segment and didn't get an answer. > > Is there a library (bonus would be some tutorial material) for making sure my > Linux scripts access files and directories on the other platforms > transparently? I don't need the information immediately, but at some point... You could go all out and use the PyFilesystem module: http://packages.python.org/fs/ This provides a unified API not only for accessing files on your local disk in a platform-agnostic manner, but also for accessing files in a zip archive, on a remote server, in memory, and from a variety of other sources. Even if you only ever intend to access local files, I find the API provided by PyFilesystem much nicer than using the various modules from the stdlib. Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
PyCon Australia 2011: Early Bird Closing Soon
Hi Everyone, A reminder that Early Bird Registrations for PyCon Australia 2011 will be closing soon. There are only a few days left to get your tickets at the discounted rate. PyCon Australia is Australia's only conference dedicated exclusively to the Python programming language, and will be held at the Sydney Masonic Center over the weekend of August 20 and 21. See below for more information and updates on: 1. Early-Bird Registration Closing Soon 2. Presentations Selected 3. More Sponsors Announced Please pass this message on to those you feel may be interested. Early-Bird Registration Closing Soon Early-bird registration closes at the end of May, so you've only got a few days left to get your tickets at the special discounted rate. We offer three levels of registration for PyCon Australia 2011. Registration provides access to two full days of technical content presented by Python enthusiasts from around the country, as well as the new classroom track and a seat at the conference dinner. Full (Early Bird) - $165 This is the registration rate for regular attendees. We are offering a limited Early Bird rate for the first 50 registrations until the end of May. Once the early-bird period ends, Full Registration will be $198. Corporate - $440 If your company is paying for you to attend PyCon, please register at the corporate rate. You'll be helping to keep the conference affordable for all. Student - $44 For students able to present a valid student card we're offering this reduced rate, which does not include the conference dinner. All prices include GST. For more information or to register, please visit the conference website. Register here: http://pycon-au.org/reg Presentations Selected == We have had a fantastic response to our Call For Proposals this year. While the detailed talk schedule is still being finalised, we are pleased to announce that the following presentations have been selected for the conference: Standard Talks: A Python on the Couch (Mark Rees) Behaviour Driven Development (Malcolm Tredinnick) Benchmarking stuff made ridiculously easy (Tennessee Leeuwenburg) Bytecode: What, Why, and How to Hack it (Ryan Kelly) Developing Scientific Software in Python (Duncan Gray) Fun with App Engine 1.5.0 (Greg Darke) Hosting Python Web Applications (Graham Dumpleton) How Python Evolves (and How You Can Help Make It Happen) (Nick Coghlan) Infinite 8-bit Platformer (Chris McCormick) Networking Libraries in Python. (Senthil Kumaran) Pants - Network Programming Made Easy (Evan Davis) Say What You Mean: Meta-Programming a Declarative API (Ryan Kelly) State of CPython and Python Ecosystem (Senthil Kumaran) Sysadmins vs Developers, a take from the other side of the fence (Benjamin Smith) Teaching Python to the young and impressionable (Katie Bell) The NCSS Challenge: teaching programming via automated testing (Tim Dawborn) Weather field warping using Python. (Nathan Faggian) Zookeepr: Home-grown conference management software (Brianna Laugher) In-Depth Talks: Ah! I see you have the machine that goes "BING"! (Graeme Cross) Easy site migration using Diazo and Funnelweb (Adam Terrey) How to maintain big app stacks without losing your mind (Dylan Jay) Introduction to the Geospatial Web with GeoDjango (Javier Candeira) Panel: Python 3 (Richard Jones) Panel: Python in the webs (Richard Jones) Pyramid: Lighter, faster, better web apps (Dylan Jay) Web micro-framework battle (Richard Jones) Classroom Track: Meta-matters: using decorators for better Python programming (Graeme Cross) Python 101+ (Peter Lovett) Python's dark corners - the bad bits in Python and how to avoid them (Peter Lovett) Python for Science and Engineering, Part 1 (Edward Schofield) Python for Science and Engineering, Part 2 (Edward Schofield) The Zen of Python (Richard Jones) Thanks again to everyone who submitted a proposal. More Sponsors Announced === We are delighted to announce that WingWare and Superior Recruitment have joined as Silver Sponsors. Thank you to the following companies for their continuing support of Python and for helping to make PyCon Australia 2011 a reality: Gold: Google <http://www.google.com.au/> Gold: ComOps <http://www.comops.com.au/> Silver: Anchor<http://anchor.com.au/> Silver: Enthought <http://www.enthought.com/> Silver: Python Software Foundation<http://www.python.org/psf/> Silver: WingWare <http://www.wingware.com/> Silver: Superior Recruitmen
Re: Python's super() considered super!
On Fri, 2011-05-27 at 15:05 +, Duncan Booth wrote: > sturlamolden wrote: > > I really don't like the Python 2 syntax of super, as it violates > > the DRY principle: Why do I need to write super(type(self),self) > > when super() will do? Assuming that 'self' will always be named > > 'self' in my code, I tend to patch __builtins__.super like this: > > > > import sys > > def super(): > > self = sys._getframe().f_back.f_locals['self'] > > return __builtins__.super(type(self),self) > > > > This way the nice Python 3.x syntax can be used in Python 2.x. > > > > > Oh dear, you haven't thought this one through. > > ...snip... > > >>> C().foo() > ... infinite recursion follows ... > > Oops. There's a reason why Python 2 requires you to be explicit about > the class; you simply cannot work it out automatically at run time. > Python 3 fixes this by working it out at compile time, but for Python 2 > there is no way around it. Oh? There's not much that can't be done at runtime if you're willing to work hard enough. Let me propose the following awful awful hack: import sys _builtin_super = __builtins__.super _sentinel = object() def _auto_super(typ=_sentinel,type_or_obj=_sentinel): """Automagically call correct super() at runtime""" # Infer the correct call if used without arguments. if typ is _sentinel: # We'll need to do some frame hacking. f = sys._getframe(1) # Get the first positional argument of the function. type_or_obj = f.f_locals[f.f_code.co_varnames[0]] # Get the MRO for investigation try: mro = type_or_obj.__mro__ except AttributeError: try: mro = type_or_obj.__class__.__mro__ except AttributeError: raise RuntimeError("super() used with old-style class") # Now, find the class owning the currently-executing method. for typ in mro: for meth in typ.__dict__.itervalues(): if not isinstance(meth,type(_auto_super)): continue if meth.func_code is f.f_code: # Aha! Found you. break else: continue break else: raise RuntimeError("super() called outside a method") # Now just dispatch to builtin super. if type_or_obj is not _sentinel: return _builtin_super(typ,type_or_obj) return _builtin_super(typ) Now, try is with the following: class Base(object): def hello(self,msg): print "hello", msg class Sub1(Base): def hello(self,msg): print "gunna say it" super().hello(msg) class Sub2(Base): def hello(self,msg): print "yes I am" super().hello(msg) class Diamond(Sub1,Sub2): def hello(self,msg): print "here we go..." super().hello(msg) d = Diamond() d.hello("autosuper!") And you get the expected output: here we go... gunna say it yes I am hello autosuper! There may well be some cases where this breaks down, but it seems to do the right thing in simple cases. Not that I'm recommending anyone use this, of course... Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
PyCon Australia 2011: cfp closing soon!
Hi Everyone, A reminder that the Call for Proposals for PyCon Australia 2011 will be closing soon. We've had some great proposals so far, but there is still time left and program to fill. PyCon Australia is Australia's only conference dedicated exclusively to the Python programming language, and will be held at the Sydney Masonic Center over the weekend of August 20 and 21. See below for more information and updates on: 1. Call For Proposals 2. More Sponsors Announced Please pass this message on to those you feel may be interested. Call For Proposals == The deadline for proposal submission is the 2nd of May. That's only a few days away! We are looking for proposals for talks on all aspects of Python programming from novice to advanced levels; applications and frameworks, or how you have been involved in introducing Python into your organisation. We're especially interested in short presentations that will teach conference-goers something new and useful. Can you show attendees how to use a module? Explore a Python language feature? Package an application? We welcome first-time speakers; we are a community conference and we are eager to hear about your experience. If you have friends or colleagues who have something valuable to contribute, twist their arms to tell us about it! Please also forward this Call for Proposals to anyone that you feel may be interested. The earlier you submit your proposal, the more time we will have to review and give you feedback before the program is finalised. Speakers receive free registration for the conference, including a seat at the conference dinner. Don't miss out, submit your proposal today! http://pycon-au.org/cfp More Sponsors Announced === We are delighted to announce that ComOps has joined as a Gold Sponsor. Thank you to the following companies for their continuing support of Python and for helping to make PyCon Australia 2011 a reality: Gold: Google <http://www.google.com.au/> Gold: Microsoft <http://www.microsoft.com.au/> Gold: ComOps <http://www.comops.com.au/> Silver: Anchor<http://anchor.com.au/> Silver: Enthought <http://www.enthought.com/> Silver: Python Software Foundation<http://www.python.org/psf/> Thanks also to Linux Australia, who provide the overarching legal and organisational structure for PyCon Australia. Ryan Kelly PyCon Australia 2011 -- http://mail.python.org/mailman/listinfo/python-list
Re: Read-write lock for Python
On Thu, 2011-04-28 at 07:02 -0700, Geoff Bache wrote: > Hi all, > > I currently find myself needing a Python read-write lock. I note that > there is none in the standard library, but googling "python read-write > lock" quickly produced 6 different competing examples, including two > languishing patch proposals for the standard library. > > I can always pick a random one and hope for the best, but I was hoping > someone here might have a tip for one that has been used and debugged > and is likely to work. I wrote and have used the "SHLock" class in threading2 which should do what you need. Don't know about "likely to work" but if it doesn't, I'd like to hear about it so I can fix it :-) `pip install threading2` Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: minimal python27.dll?
On Wed, 2011-04-27 at 22:06 +0200, Martin v. Loewis wrote: > Am 27.04.2011 12:43, schrieb est: > > Hi guys, > > > > I need to ship python runtime environment package on Windows, if I > > want to stripping unnessasery functions from python27.dll to make it > > as small as possible(and perhaps finally UPX it), which parts of > > python27.dll do you think can be removed? > > > > I'd rather go for a static build of Python, and let the linker figure > out what's needed. I have vague recollections that pythonXY.dll could not be statically linked on Windows, or that doing so causes some serious loss of functionality. Was this ever true, and is it still? Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
PyCon Australia 2011: registrations now open
Hi Everyone, I'm pleased to announce that registrations are now open for PyCon Australia 2011. PyCon Australia is Australia's only conference dedicated exclusively to the Python programming language, and will be held at the Sydney Masonic Center over the weekend of August 20 and 21. See below for more information and updates on: 1. Registration is now open 2. Classroom Track 3. Call For Proposals deadline approaching 4. Sponsors Announced Please pass this message on to those you feel may be interested. Registration Is Now Open We offer three levels of registration for PyCon Australia 2011. Registration provides access to two full days of technical content presented by Python enthusiasts from around the country, as well as the new classroom track and a seat at the conference dinner. We are currently offering a limited number of early-bird tickets, but get in quick because they are selling fast! Corporate - $440 If your company is paying for you to attend PyCon, please register at the corporate rate. You'll be helping to keep the conference affordable for all. Full (Early Bird) - $165 This is the registration rate for regular attendees. We are offering a limited Early Bird rate for the first 50 registrations until the end of May. Student - $44 For students able to present a valid student card we're offering this reduced rate, which does not include the conference dinner. All prices include GST. For more information or to register, please visit the conference website. Register here: http://pycon-au.org/reg Classroom Track === In addition to the standard technical talks, this year's conference will feature a "Classroom Track" designed specifically for tutorial style presentations. If you need to get up to speed on some of the latest language features and tools, this will be a great opportunity to learn fast in a supportive environment. Call For Proposals == We've had some great initial responses to the Call For Proposals, but there's still time left and plenty of program to fill. Remember, the deadline for proposal submission is the 2nd of May. That's just under two weeks away! We are looking for proposals for talks on all aspects of Python programming from novice to advanced levels; applications and frameworks, or how you have been involved in introducing Python into your organisation. We're especially interested in short presentations that will teach conference-goers something new and useful. Can you show attendees how to use a module? Explore a Python language feature? Package an application? We welcome first-time speakers; we are a community conference and we are eager to hear about your experience. If you have friends or colleagues who have something valuable to contribute, twist their arms to tell us about it! Please also forward this Call for Proposals to anyone that you feel may be interested. The earlier you submit your proposal, the more time we will have to review and give you feedback before the program is finalised. Speakers receive free registration for the conference, including a seat at the conference dinner. Don't miss out, submit your proposal today! http://pycon-au.org/cfp Sponsors Announced == We are happy to announce our first set of sponsors. Thank you to the following companies for their continuing support of Python and for helping to make PyCon Australia 2011 a reality: Gold: Google <http://www.google.com.au/> Gold: Microsoft <http://www.microsoft.com.au/> Silver: Anchor<http://anchor.com.au/> Silver: Enthought <http://www.enthought.com/> Silver: Python Software Foundation<http://www.python.org/psf/> Thanks also to Linux Australia, who provide the overarching legal and organisational structure for PyCon Australia. Ryan Kelly PyCon Australia 2011 -- http://mail.python.org/mailman/listinfo/python-list
Re: Pythonic infinite for loop?
On Fri, 2011-04-15 at 12:34 +1000, Ryan Kelly wrote: > On Fri, 2011-04-15 at 12:10 +1000, Chris Angelico wrote: > > > > > > My first draft looks something like this. The input dictionary is > > called dct, the output list is lst. > > > > lst=[] > > for i in xrange(1,1000): # arbitrary top, don't like this > > try: > > lst.append(parse_kwdlist(dct["Keyword%d"%i])) > > except KeyError: > > break > > > It might be even easier to just iterate through the dictionary keys: > > for k in sorted(dct.keys()): > if k.startswith("Keyword"): > lst.append(parse_kwdlist(dct[k])) Actually sorted() won't work here, since it sorts lexicographically. So you'd wind up with "Keyword111" before "Keyword2". You would have to sort after extracting the necessary info (assuming order is actually important in the final list) Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Pythonic infinite for loop?
On Fri, 2011-04-15 at 12:10 +1000, Chris Angelico wrote: > Apologies for interrupting the vital off-topic discussion, but I have > a real Python question to ask. > > I'm doing something that needs to scan a dictionary for elements that > have a particular beginning and a numeric tail, and turn them into a > single list with some processing. I have a function parse_kwdlist() > which takes a string (the dictionary's value) and returns the content > I want out of it, so I'm wondering what the most efficient and > Pythonic way to do this is. > > My first draft looks something like this. The input dictionary is > called dct, the output list is lst. > > lst=[] > for i in xrange(1,1000): # arbitrary top, don't like this > try: > lst.append(parse_kwdlist(dct["Keyword%d"%i])) > except KeyError: > break > > I'm wondering two things. One, is there a way to make an xrange object > and leave the top off? (Sounds like I'm risking the numbers > evaporating or something.) There is, use an infinite generator: def ints_from(start): while True: yield start start += 1 for i in ints_from(1): ..etc... But why not just put the while loop inline: i = 0 while True: try: ...etc... except KeyError: break i += 1 It might be even easier to just iterate through the dictionary keys: for k in sorted(dct.keys()): if k.startswith("Keyword"): lst.append(parse_kwdlist(dct[k])) > And two, can the entire thing be turned > into a list comprehension or something? Generally any construct with a > for loop that appends to a list is begging to become a list comp, but > I can't see how to do that when the input comes from a dictionary. You probably could, but I think it would hurt readability in this case: lst = [parse_kwdlist(dct[k]) for k in sorted(dct.keys()) if k.startswith("Keyword")] Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Egos, heartlessness, and limitations
On Thu, 2011-04-14 at 03:12 +, Steven D'Aprano wrote: > On Thu, 14 Apr 2011 12:03:15 +1000, Ryan Kelly wrote: > > > On Thu, 2011-04-14 at 11:46 +1000, Chris Angelico wrote: > >> On Thu, Apr 14, 2011 at 11:29 AM, Ryan Kelly wrote: > >> > I weep that your delightful rhetoric is limited to this neglected > >> > forum, where the guardians of python core deign not to tread, and > >> > hence denied its rightful place exalted among python's canonical > >> > lore. > >> > >> Wait... so where do the Python experts hang out? > > > > Don't panic, there are plenty of experts here :-) > > > > It's an oft-cited troll complaint that many python big-wigs (Guido, > > Raymond H, et al) don't subscribe to python-list. > > Raymond Hettinger frequently posts here, both with interesting code > snippets and recipes, and to answer questions. True. Sorry Raymond. You just happened to be the second name that popped into my head in the "python big-wig" category. > Personally, I'm glad that most of Python Dev don't hang around here. We > are far better off if Python Dev, you know, actually Devs Python, rather > than answering (mostly) easy questions and getting stuck in tar-pits. For the record, I have no personal complaint about anyone's lack of involvement on python-list. Just reporting on the perceived state of affairs. Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Egos, heartlessness, and limitations
On Wed, 2011-04-13 at 19:10 -0700, rantingrick wrote: > On Apr 13, 8:29 pm, Ryan Kelly wrote: > > On Wed, 2011-04-13 at 17:39 -0700, rantingrick wrote: > > I would LOVE to improve the doc, however first the student THEN the > teacher. However in this forsaken land the "teachers" do not exist. We > are cast off from the elites and left to wither, wandering in dark > catacombs of source code with many doors but no keys to unlock them. > > [..snip..] > > The "elites" have hidden themselves behind an > impenetrable wall called python-dev. They wish not to speak with the > peasants. Funny you should bring that up. The folks on python-dev are currently making a substantial push to increase involvement in python core development through the "Python Mentors" program. Site here: http://pythonmentors.com/ To quote from the site: """ The mission of the Python Core Mentor Program is to provide an open and welcoming place to connect students, programmers – and anyone interested in contributing to the Python Core development. This project is based on the idea that the best way to welcome new people into any project is a venue which connects them to a variety of mentors who can assist in guiding them through the contribution process, including discussions on lists such as python-dev, and python-ideas, the bug tracker, mercurial questions, code reviews, etc. """ So anyone following along this thread, if you're interested in making a genuine contribution to python as a language, this is a great time and place to start. Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Egos, heartlessness, and limitations
On Thu, 2011-04-14 at 11:46 +1000, Chris Angelico wrote: > On Thu, Apr 14, 2011 at 11:29 AM, Ryan Kelly wrote: > > I weep that your delightful rhetoric is limited to this neglected forum, > > where the guardians of python core deign not to tread, and hence denied > > its rightful place exalted among python's canonical lore. > > Wait... so where do the Python experts hang out? Don't panic, there are plenty of experts here :-) It's an oft-cited troll complaint that many python big-wigs (Guido, Raymond H, et al) don't subscribe to python-list. Personally I've never really noticed - even if some of the core devs don't really hang out here, I've always found python-list full of helpful and knowledgeable people. It's also an oft-cited troll conspiracy that Guido hangs out on python-list and posts under various pseudonyms. I think it would be kinda fun if he did... Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Egos, heartlessness, and limitations
On Wed, 2011-04-13 at 17:39 -0700, rantingrick wrote: > > - > 1. Poor documentation (or lack thereof): > - > Everyone knows that dcoumentation is important however at the end of > the day laziness is the rule of thumb for profesionals and weekend > teckies alike. But why be a part of any open source community and > propagate laziness? We must be more strict about doumentation. However > it seems the age old policies of "it's not what you know, but *who* > you know" or more correct;y adapted tot he situation at hand..."it's > not imprtant how well you document a module *unless* you are not a > goodfella (psst: a memeber of Guido inc). Oh rr, if only the time you spent formulating such eloquent prose could be devoted instead to improving the documentation whose state you bemoan. I weep that your delightful rhetoric is limited to this neglected forum, where the guardians of python core deign not to tread, and hence denied its rightful place exalted among python's canonical lore. > I have enlightened this group long ago of the > limitless possibilities of IDLE to be a good primer for our budding > young programmers however like all my great brain children this one > has been cast aside like a red headed stepchild. I can only imagine the hi-jinx that ensure at your yearly great brain family reunion. Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Is this a safe use of eval?
On Thu, 2011-02-24 at 20:13 +1100, Ryan Kelly wrote: > On Thu, 2011-02-24 at 10:48 +0200, Frank Millman wrote: > > Hi all > > > > I know that the use of 'eval' is discouraged because of the dangers of > > executing untrusted code. > > > > Here is a variation that seems safe to me, but I could be missing something. > > > > I have a class, and the class has one or more methods which accept various > > arguments and return a result. > > > > I want to accept a method name and arguments in string form, and 'eval' it > > to get the result. > > > > Assume I have an instance called my_inst, and a method called 'calc_area', > > with arguments w and h. > > > > I then receive my_string = 'calc_area(100, 200)'. > > > > >>> result = eval('my_inst.{0}'.format(my_string)) > > > > This will only work if the string contains a valid method name with valid > > arguments. > > > > Can anyone see anything wrong with this? > > Yes. A serious problem. > > > But actually it allows all sorts of nasty things. Watch me open an > arbitrary file on your system (assuming you have permission of course). > > >>> > testit('__class__.__mro__[-1].__subclasses__()[58]("/secret/file","w")') > Traceback (most recent call last): > File "", line 1, in > File "", line 2, in testit > File "", line 1, in > IOError: [Errno 2] No such file or directory: '/secret/file' > >>> Just to elaborate a little more. Once you've got a reference to 'object' the game it pretty much over - you can walk its subclasses to get to all kinds of nasty things like 'file'. Since this was a newstyle class, getting to 'object' was easy - it's always the class's final base class (i.e. __mro__[-1]). You might think that using an old-style class would save you: >>> class MyClass: ... pass ... >>> inst = MyClass() >>> inst.__class__.__mro__[-1] Traceback (most recent call last): File "", line 1, in AttributeError: class MyClass has no attribute '__mro__' But there will almost always be a reference to a builtin type hanging around somewhere. Builtin types are all newstyle classes, and hence have 'object' in their mro. For example: >>> inst.__dict__.__class__.__mro__[-1] >>> Or perhaps: >>> inst.__class__.__name__.__class__.__mro__[-1] It's pretty much impossible to prevent this kind of thing in python. You might get away with it if you parse the string looking for suspicious characters e.g. dots. But that will limit your grammar and I won't be surprised if there's still a way around it. > So please, don't do this! :-) So what's the alternative? As suggested by another poster, for simple cases use the ast.literal_eval function. For anything more complicated, use PyParsing to generate your own mini language and interpret it yourself. It's really pretty simple once you get in the right head-space. Try some of the links from this SO post if you want to start down this path: http://stackoverflow.com/questions/1545403/math-expression-evaluation Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Is this a safe use of eval?
On Thu, 2011-02-24 at 10:48 +0200, Frank Millman wrote: > Hi all > > I know that the use of 'eval' is discouraged because of the dangers of > executing untrusted code. > > Here is a variation that seems safe to me, but I could be missing something. > > I have a class, and the class has one or more methods which accept various > arguments and return a result. > > I want to accept a method name and arguments in string form, and 'eval' it > to get the result. > > Assume I have an instance called my_inst, and a method called 'calc_area', > with arguments w and h. > > I then receive my_string = 'calc_area(100, 200)'. > > >>> result = eval('my_inst.{0}'.format(my_string)) > > This will only work if the string contains a valid method name with valid > arguments. > > Can anyone see anything wrong with this? Yes. A serious problem. Here's an example of what you describe: >>> class MyClass(object): ... def calc_area(self,x,y): ... return 42 ... >>> inst = MyClass() >>> >>> def testit(query): ... return eval("inst.{0}".format(query)) >>> It works as you expect when used properly: >>> testit('calc_area(3,4)') 42 But actually it allows all sorts of nasty things. Watch me open an arbitrary file on your system (assuming you have permission of course). First find out how to access the "file" builtin: >>> testit('__class__.__mro__[-1].__subclasses__().index(file)') 58 Great, plug that in and we're in business: >>> testit('__class__.__mro__[-1].__subclasses__()[58]("/secret/file","w")') Traceback (most recent call last): File "", line 1, in File "", line 2, in testit File "", line 1, in IOError: [Errno 2] No such file or directory: '/secret/file' >>> So please, don't do this! :-) Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: If/then style question
On Thu, 2010-12-16 at 21:49 +, John Gordon wrote: > (This is mostly a style question, and perhaps one that has already been > discussed elsewhere. If so, a pointer to that discussion will be > appreciated!) > > When I started learning Python, I wrote a lot of methods that looked like > this: > > > def myMethod(self, arg1, arg2): > if some_good_condition: > if some_other_good_condition: > if yet_another_good_condition: > do_some_useful_stuff() > exitCode = good1 > else: > exitCode = bad3 > else: > exitCode = bad2 > else: > exitCode = bad1 > return exitCode > > > But lately I've been preferring this style: > > > def myMethod(self, arg1, arg2): > if some_bad_condition: > return bad1 > elif some_other_bad_condition: > return bad2 > elif yet_another_bad_condition: > return bad3 > do_some_useful_stuff() > return good1 > > I like this style more, mostly because it eliminates a lot of indentation. > > However I recall one of my college CS courses stating that "one entry, > one exit" was a good way to write code, and this style has lots of exits. > > Are there any concrete advantages of one style over the other? "one entry, one exit" has its good points, but it's *way* overquoted and overused. Do you raise any exceptions? Do you call any functions that might raise exceptions? If so, you've got multiple exit points already. I think this style a lot more important in a language like C where you have to be super-careful about cleaning up after yourself. The single exit point makes it easier to verify that all cleanup tasks have been performed. Assuming you're using "with" or "try-finally" then you just don't need such guarantees in python. I'm not a PEP-8 pedant by any means, but I think that the first section of PEP-8 contains the best advice I've ever read about programming language style. In fact, I'm going to quote it right here: A Foolish Consistency is the Hobgoblin of Little Minds == One of Guido's key insights is that code is read much more often than it is written. The guidelines provided here are intended to improve the readability of code and make it consistent across the wide spectrum of Python code. As PEP 20 says, "Readability counts". ...snip... But most importantly: know when to be inconsistent -- sometimes the style guide just doesn't apply. When in doubt, use your best judgment. Look at other examples and decide what looks best. And don't hesitate to ask! In your example, the first style is difficult to read wile the second style is easy to read. You don't need any further justification for preferring the latter. Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: performance of tight loop
On Tue, 2010-12-14 at 08:08 +0100, Ulrich Eckhardt wrote: > Steven D'Aprano wrote: > > Replacing "while True" with "while 1" may save a tiny bit of overhead. > > Whether it is significant or not is another thing. > > Is this the price for an intentional complexity or just a well-known > optimizer deficiency? At least on older pythons, you can assign to the name "True" so it's not possible to optimize that loop - you must look up the name "True" on each iteration. For example, in python 2.6 this loop will exit after one iteration: >>> while True: ... True = False ... >>> To see the difference, take a look at the bytecode python generators for the type types of loop: >>> import dis >>> def while1(): ... while 1: ... pass ... >>> def whileTrue(): ... while True: ... pass ... >>> dis.dis(while1) 2 0 SETUP_LOOP 3 (to 6) 3 >>3 JUMP_ABSOLUTE3 >>6 LOAD_CONST 0 (None) 9 RETURN_VALUE >>> >>> dis.dis(whileTrue) 2 0 SETUP_LOOP 12 (to 15) >>3 LOAD_GLOBAL 0 (True) 6 JUMP_IF_FALSE4 (to 13) 9 POP_TOP 3 10 JUMP_ABSOLUTE3 >> 13 POP_TOP 14 POP_BLOCK >> 15 LOAD_CONST 0 (None) 18 RETURN_VALUE >>> Still, I just can't bring myself to write "while 1" in favour of "while True" in code. Python 3 does away with this madness entirely: >>> while True: ... True = False ... File "", line 2 SyntaxError: assignment to keyword >>> Looking at the bytecode shows that in Python 3, "while 1" and "while True" are indeed identical. Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Weird try-except vs if behavior
On Thu, 2010-10-14 at 22:43 -0700, James Matthews wrote: > Hi, > > I have this code http://gist.github.com/627687 (I don't like pasting > code into the mailing list). Yes, but it makes it harder to discuss the ode and makes the archive that much more useless. It's only a couple of lines, here ya go: def tryway(): try: while True: alist.pop() except IndexError: pass def ifway(): while True: if blist == []: break else: blist.pop() if __name__=='__main__': alist = range(1000) blist = range(1000) from timeit import Timer print "Testing Try" tr = Timer("tryway()","from __main__ import tryway") print tr.timeit() print "Testing If" ir = Timer("ifway()","from __main__ import ifway") print ir.timeit() > I am wondering why the try except is taking longer. I assume that if > the IF statement checks every iteration of the loop (1000 times) > shouldn't it be slower? You're not measuring what you think. The way you've structured your code, "alist" and "blist" are module globals. Timeit will call the "tryway" function one million times in a loop. The first time it works as you expect, popping each element off of "alist" in turn. On the other 99 executions, "alist" is already empty (having been emptied by the first execution) and the IndexError is raised immediately. Likewise for the execution of "ifway". So what you're really measuring is the overhead of catching an exception versus testing a condition for an *empty* list - no surprise that the conditional version is faster! If you re-initialise the list at the beginning of each function, the try-based version is faster as you expect. I.e.: def tryway(): alist = range(1000) try: while True: alist.pop() except IndexError: pass I get the following times for a thousand iterations (not waiting around for a million!) Testing Try 0.224129915237 Testing If 0.300312995911 Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Standardizing RPython - it's time.
On Mon, 2010-10-11 at 13:01 -0700, John Nagle wrote: > It may be time to standardize "RPython". > >There are at least three implementations of "RPython" variants - PyPy, > Shed Skin, and RPython for LLVM. The first two are up and running. > There's a theory paper on the subject: > > http://citeseerx.ist.psu.edu/viewdoc/download?doi=10.1.1.142.1457&rep=rep1&type=pdf > >All three have somewhat different restrictions: > > PyPy's Rpython: > http://codespeak.net/pypy/dist/pypy/doc/coding-guide.html > > Shed Skin: > file:///C:/Users/nagle/AppData/Local/Temp/shedskin-tutorial-0.3.html > > Rpython for LLVM: > http://code.google.com/p/rpython/ > > So a language standardization effort, independent of CPython, > would be useful. A similar topic was recently discussed on the pypy-dev mailing list: http://codespeak.net/pipermail/pypy-dev/2010q3/006170.html My interpretation is that the pypy devs are -0 on such a standardisation effort, as it would give them less flexibility in moulding rpython for their specific needs. Adding features to rpython that make it better as a general-purpose programming language could actually make it *worse* as a specialised language for building pypy. OTOH, there does seem to be a growing interest in using rpython as a stand-alone language. I've used it for some small projects and it worked out great. But the intersection of (people who want rpython as a general-purpose language) and (people who have the ability to make that happen) seems to be approximately zero at the moment... Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Private variables
On Thu, 2010-09-02 at 12:06 +1000, Ryan Kelly wrote: > On Thu, 2010-09-02 at 11:10 +1000, Rasjid Wilcox wrote: > > Hi all, > > > > I am aware the private variables are generally done via convention > > (leading underscore), but I came across a technique in Douglas > > Crockford's book "Javascript: The Good Parts" for creating private > > variables in Javascript, and I'd thought I'd see how it translated to > > Python. Here is my attempt. > > > > def get_config(_cache=[]): > > private = {} > > private['a'] = 1 > > private['b'] = 2 > > if not _cache: > > class Config(object): > > @property > > def a(self): > > return private['a'] > > @property > > def b(self): > > return private['b'] > > config = Config() > > _cache.append(config) > > else: > > config = _cache[0] > > return config > > > > >>> c = get_config() > > >>> c.a > > 1 > > >>> c.b > > 2 > > >>> c.a = 10 > > Traceback (most recent call last): > > File "", line 1, in > > AttributeError: can't set attribute > > >>> dir(c) > > ['__class__', '__delattr__', '__dict__', '__doc__', '__format__', > > '__getattribute__', '__hash__', '__init__', '__module__', '__new__', > > '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', > > '__sizeof__', '__str__', '__subclasshook__', '__weakref__', 'a', 'b'] > > >>> d = get_config() > > >>> d is c > > True > > > > I'm not really asking 'is it a good idea' but just 'does this work'? > > It seems to work to me, and is certainly 'good enough' in the sense > > that it should be impossible to accidentally change the variables of > > c. > > > > But is it possible to change the value of c.a or c.b with standard > > python, without resorting to ctypes level manipulation? > > It's not easy, but it can be done by introspecting the property object > you created and munging the closed-over dictionary object: > >>>> c = get_config() >>>> c.a >1 >>>> c.__class__.__dict__['a'].fget.func_closure[0].cell_contents['a'] = 7 >>>> c.a >7 >>>> Heh, and of course I miss the even more obvious trick of just clobbering the property with something else: >>> c.a 1 >>> setattr(c.__class__,"a",7) >>> c.a 7 >>> Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Private variables
On Thu, 2010-09-02 at 11:10 +1000, Rasjid Wilcox wrote: > Hi all, > > I am aware the private variables are generally done via convention > (leading underscore), but I came across a technique in Douglas > Crockford's book "Javascript: The Good Parts" for creating private > variables in Javascript, and I'd thought I'd see how it translated to > Python. Here is my attempt. > > def get_config(_cache=[]): > private = {} > private['a'] = 1 > private['b'] = 2 > if not _cache: > class Config(object): > @property > def a(self): > return private['a'] > @property > def b(self): > return private['b'] > config = Config() > _cache.append(config) > else: > config = _cache[0] > return config > > >>> c = get_config() > >>> c.a > 1 > >>> c.b > 2 > >>> c.a = 10 > Traceback (most recent call last): > File "", line 1, in > AttributeError: can't set attribute > >>> dir(c) > ['__class__', '__delattr__', '__dict__', '__doc__', '__format__', > '__getattribute__', '__hash__', '__init__', '__module__', '__new__', > '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', > '__sizeof__', '__str__', '__subclasshook__', '__weakref__', 'a', 'b'] > >>> d = get_config() > >>> d is c > True > > I'm not really asking 'is it a good idea' but just 'does this work'? > It seems to work to me, and is certainly 'good enough' in the sense > that it should be impossible to accidentally change the variables of > c. > > But is it possible to change the value of c.a or c.b with standard > python, without resorting to ctypes level manipulation? It's not easy, but it can be done by introspecting the property object you created and munging the closed-over dictionary object: >>> c = get_config() >>> c.a 1 >>> c.__class__.__dict__['a'].fget.func_closure[0].cell_contents['a'] = 7 >>> c.a 7 >>> Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Python "why" questions
On Fri, 2010-08-06 at 22:05 -0500, Default User wrote: > >From "the emperor's new clothes" department: > > 1) Why do Python lists start with element [0], instead of element > [1]? "Common sense" would seem to suggest that lists should start > with [1]. "Common sense" is wrong. There are many compelling advantages to numbering from zero instead of one: http://lambda-the-ultimate.org/node/1950 > 2) In Python 3, why is print a function only, so that: print "Hello, > World" is not okay, but it must be print("Hello, World") instead? > (Yeah, I know: picky, picky . . . ) The real question is, why was print so special in Python 2 that is can be called without parentheses? The answer was "no reason" and it was fixed in Python 3 to be consistent with the rest of the language. > 3) In Python 3, why does 2.0 / 3.0 display as 0., but > 8 * 3.57 displays as 28.56 (rounded off to 2 decimal places)? And > yet, in Python 2.6, 8 * 3.57 displays as 28.559? Because the code for displaying floats was improved in python 3. You can follow the fascinating discussion on issue 7117: http://bugs.python.org/issue7117 I can't defend the rounding issues of floating point numbers in general - it's just "one of those things" that you have to deal with. But show me a language where floats don't have this problem. > And we wonder why kids don't want to learn to program. Yeah, obscure language warts, that must be the reason. Note to self: DNFTT... Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details -- http://mail.python.org/mailman/listinfo/python-list
Re: subprocess escaping POpen?!
On Thu, 2010-08-05 at 12:58 +0100, Chris Withers wrote: > Jean-Michel Pichavant wrote: > > You did not redirect stdin, so it is expected you can still read input > > from the console. > > Okay, so if I definitely wanted no input, what should I pass as the > stdin parameter to the POpen constructor? The cross-platform equivalent of /dev/null: Popen(...,stdin=open(os.devnull,"r")...) > > And it looks like svn is writting the credentials > > prompt on stderr. > > ...which, as you can see from the code I posted, is piped to STDOUT, > which is then PIPE'd through to the calling python so that > communicate()'s return value will contain the output. > > As I explained, I can't reproduce this by replacing svn with a simple > python script that writes to stderr. So, what is svn doing? Many programs prompt for auth credentials on the controlling tty instead of standard input/output. I believe SSH also does this, which suggests that it's considered more secure. No idea why, but I trust the authors of SSH to know their stuff in this regard. Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details -- http://mail.python.org/mailman/listinfo/python-list
Re: sending a file chunk by chunk instead as a whole to a web server
On Tue, 2010-08-03 at 10:45 +0530, Kushal Kumaran wrote: > On Mon, Aug 2, 2010 at 12:22 PM, Sanjeeb wrote: > > Hi, > > I have a web client which send a file to a server as multipart form > > data, the sending of data is from > > http://code.activestate.com/recipes/146306-http-client-to-post-using-multipartform-data/. > > > > I dont want to open the whole file to memory(at cliend end) and then > > send, i just want to send part by part, say chunk of 1024 bytes to the > > server and then assemble at the server end. > > > > Could some one suggest what would be the best way to do this? > > > > There's no reason why sending the whole file implies reading the whole > file into memory at one time. You can just read your desired chunk > size and send it, then read the next chunk, and so on. You might have > to first find the total size to calculate what to set Content-Length > to. More concretely, you would restructure the encode_multipart_formdata() function as a generator, yielding chunks of data to send one at a time. Something like this: def post_multipart(host,selector,fields,files): ...snip... h.endheaders() for chunk in encode_multipart_formdata_chunks(fields,files): h.send(chunk) errcode, errmsg, headers = h.getreply() return h.file.read() def encode_multipart_formdata(fields,files): BOUNDARY = '--ThIs_Is_tHe_bouNdaRY_$' CRLF = '\r\n' for (key, value) in fields: yield '--' + BOUNDARY yield 'Content-Disposition: form-data; name="%s"' % key yield '' yield value for (key, filename, value) in files: yield '--' + BOUNDARY yield 'Content-Disposition: form-data; name="%s"; filename="%s"' % (key, filename) ...etc... ...etc... There are many improvements to make, but this should get you started. For example, you'll need to calculate the total content-length rather than just calling len(body) to obtain it. That's left as an exercise to the reader. Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: A question about the posibility of raise-yield in Python
On Wed, 2010-06-30 at 16:20 -0700, ru...@yahoo.com wrote: > On Jun 30, 10:48 am, John Nagle wrote: > > On 6/30/2010 12:13 AM, Дамјан Георгиевски wrote: > > > > >> A 'raise-yield' expression would break the flow of a program just like > > >> an exception, going up the call stack until it would be handled, but > > >> also like yield it would be possible to continue the flow of the > > >> program from where it was raise-yield-ed. > > > > Bad idea. Continuing after an exception is generally troublesome. > > This was discussed during the design phase of Ada, and rejected. > > Since then, it's been accepted that continuing after an exception > > is a terrible idea. The stack has already been unwound, for example. > > > > What you want, in in the situation you describe, is an optional > > callback, to be called in case of a fixable problem. Then the > > caller gets control, but without stack unwinding. I've tried my hand at implementing the "condition/handler/restart" paradigm of common lisp, which is very similar to what you describe. You might find it useful: http://pypi.python.org/pypi/withrestart/ Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details -- http://mail.python.org/mailman/listinfo/python-list
Re: Lockless algorithms in python (Nothing to do with GIL)
On Mon, 2010-06-28 at 19:45 -0700, sturlamolden wrote: > > > Many lockless algorithms that I have looked at thusfar require a > > > "Compare and Swap" operation. Does python have an equivalent to this? > > > Is python high level enough that it has something better than this or > > > it simply doesn't need it? > > Python does have a GIL, and contrary to the title, this has a lot to > do with the GIL. Specifically, any set of operations protected by the > GIL are atomic in the CPython interpreter. > > We can therefore get global synchronization 'for free', allowing 'lock > free' data structures that avoid using threading.Lock, and replaces it > with, well, nothing. :) > > How to do it (it takes tiny amounts of C or Cython): > > Take at look at page 14: > >http://www.dabeaz.com/python/UnderstandingGIL.pdf > > The critical part is the variable _Py_Ticker in Python's source file > ceval.c, which is declared volatile int. As it is not declared static > it is a global variable, and we can actually manipulate its value from > a C extension: > >extern volatile int _Py_Ticker; // evil!!! > > Now imagine temporarily setting _Py_Ticker to some ridiculous high > value like 0x7fff. That locks out all other threads, practically > forever, until we restore _Py_Ticker back to it's original value. > > What this gives us is global synchronization for free! The GIL is > there anyway, so it adds no additional overhead. Very interesting idea. Will it work if accessed through ctypes? ticker = ctypes.c_int.in_dll(ctypes.pythonapi,"_Py_Ticker") ticker.value = 0x7fff Or does ctypes muck with the GIL in a way that would break this idea? Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Lockless algorithms in python (Nothing to do with GIL)
On Mon, 2010-06-28 at 18:27 -0700, Zac Burns wrote: > > > > I've managed to avoid locking in some cases by using > dict.setdefault() as a kind of atomic test-and-set operation. > It's not a full compare-and-swap but you could implement a > simple locking scheme using it like this: > > > class PretendLock: > def __init__(self): > self.d = dict() > def acquire(self): > myid = threading.currentThread().ident > while self.d.setdefault("owner",myid) != myid: > pass > def release(self): > del self.d["owner"] > > > This depends on some peculiarities of the CPython > implementation that aren't guaranteed by the language spec - > namely that thread switches can't happen while executing C > code, that dict.setdefault is implemented in C, and that is > can calculate the hash of a string key without calling back > out to python code. > > > Thanks Ryan, > > Agreed, I was timing the wrong thing - but largely because I wasn't > sure what to time against. setdefault certainly seems to be a > candidate for something to time. Even so, setdefault wins. > > Though, I wouldn't want to use PretendLock in this case... it doesn't > seem that having the spin loop would justify reducing reducing the > lock allocation overhead in a no-contention scenario. Oh totally - nobody reading this should even consider using that PretendLock class for anything. It's just an example of how to use setdefault as a test-and-set kind of operator. Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Lockless algorithms in python (Nothing to do with GIL)
On Mon, 2010-06-28 at 16:46 -0700, Zac Burns wrote: > In my experience it is far more expensive to allocate a lock in python > then it is the types that use them. Here are some examples: > > >>> timeit.timeit('Lock()', 'from threading import Lock') > 1.4449114807669048 > > >>> timeit.timeit('dict()') > 0.2821554294221187 > > >>> timeit.timeit('list()') > 0.17358153222312467 > > > Granted, I know these types do not allocate a lock - but a similarly > defined user type would need to allocate a lock to guarantee > thread-safety. Sure, but I think you're timing the wrong thing here. You would only allocate the lock relatively rarely - it's the overhead of *acquiring* the lock that's the real problem. r...@durian:~$ python -m timeit -s "from threading import Lock; l = Lock()" "l.acquire(); l.release()" 100 loops, best of 3: 0.378 usec per loop Compare to one of my favourite dict methods, setdefault: r...@durian:~$ python -m timeit -s "d = dict()" "d.setdefault('hello','world')" 1000 loops, best of 3: 0.189 usec per loop In the same ballpark really. > I have not done a great deal of research into lockless algorithms > thusfar, but would it be worthwhile to investigate implementing some > of them in python to optimize performance critical sections of code? > > Many lockless algorithms that I have looked at thusfar require a > "Compare and Swap" operation. Does python have an equivalent to this? > Is python high level enough that it has something better than this or > it simply doesn't need it? I've managed to avoid locking in some cases by using dict.setdefault() as a kind of atomic test-and-set operation. It's not a full compare-and-swap but you could implement a simple locking scheme using it like this: class PretendLock: def __init__(self): self.d = dict() def acquire(self): myid = threading.currentThread().ident while self.d.setdefault("owner",myid) != myid: pass def release(self): del self.d["owner"] This depends on some peculiarities of the CPython implementation that aren't guaranteed by the language spec - namely that thread switches can't happen while executing C code, that dict.setdefault is implemented in C, and that is can calculate the hash of a string key without calling back out to python code. Usually, it's not worth it. The one time I use this regularly is for lazy object initialisation, e.g. something like this: def get_my_object(key): try: return objects[key] except KeyError: return objects.setdefault(key,create_my_object(key)) If two threads happen to try initialising the object at the same time, only one will wind up in the dict and being used; the other will be discarded and garbage-collected. Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Possible to reach back in stack and grab calling function's locals()?
On Thu, 2010-06-17 at 16:02 -0400, pyt...@bdurham.com wrote: > Is there an elegant way to reach back in the stack and grab the > calling function's copy of locals()? You can do it using my favourite function, sys._getframe: >>> import sys >>> >>> def outer(): ... a = 1 ... inner() ... >>> >>> def inner(): ... print sys._getframe(1).f_locals ... >>> >>> outer() {'a': 1} >>> The dict so obtained is of course read-only. If you like I can show you the black magic necessary to *write* to the local variables of the calling function, but it ain't pretty :-) > I'm working on a library that does lots of textmerge operations and am > looking for a way to eliminate the need for many of the calls to our > library to have to explictly pass locals() to our formatting > functions. I understand the desire, but that sounds like trouble to me. Explicit is better than implicit and all that. You might get away with it for purely internal code (heck, even the standard library uses sys._getframe on occasion!) but I would hesitate to have a public-facing API that snaffles locals from any function that happens to call it. Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: withhacks module (Re: Code redundancy)
On Wed, 2010-04-21 at 19:43 -0400, pyt...@bdurham.com wrote: > Ryan, > > Your withhacks module looks very interesting. > http://pypi.python.org/pypi/withhacks > > What are your specific concerns about its use? Are there portability > concerns? It combines two things you just don't see in respectable python programs - bytecode hacking and trace-function hacking. And I'm sure its performance is less than stellar, although much of that could be fixed with some careful bytecode caching. I'd be surprised if it runs under alternative python implementations, and not surprised if it doesn't even work on Python 3 - although I haven't tried it to confirm either way. Having said that, it should work as advertised on Python 2.X with minimal fuss. So if you don't care about portability or about that dirty feeling you get from messing with the Python internals, then have at it :-) Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details -- http://mail.python.org/mailman/listinfo/python-list
Re: Code redundancy
On Tue, 2010-04-20 at 14:43 +0100, Alan Harris-Reid wrote: > Hi, > > During my Python (3.1) programming I often find myself having to repeat > code such as... > > class1.attr1 = 1 > class1.attr2 = 2 > class1.attr3 = 3 > class1.attr4 = 4 > etc. > > Is there any way to achieve the same result without having to repeat the > class1 prefix? Before Python my previous main language was Visual > Foxpro, which had the syntax... > > with class1 >.attr1 = 1 >.attr2 = 2 >.attr3 = 3 >.attr4 = 4 >etc. > endwith > > Is there any equivalent to this in Python? Please don't take this as in invitation to disregard the excellent advice already received in this thread - I just want to point out that python can usually be bent to your will. Observe: from withhacks import namespace with namespace(class1): attr1 = 1 attr2 = 2 This will do pretty much what you get from the "with" statement in javascript (I assume it's similar to Visual Foxpro). But don't use this in any real code. Seriously, don't even think about it. You don't want to know the kind of abuses that go on under the covers to make this kind of syntax hacking work... Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details -- http://mail.python.org/mailman/listinfo/python-list
Re: when should I explicitely close a file?
On Tue, 2010-04-13 at 18:19 -0700, Chris Rebert wrote: > On Tue, Apr 13, 2010 at 5:45 PM, Giampaolo Rodola' wrote: > > What about open('foo', 'w').close(). > > Does it have the same problems? > > Well, no, but that's only because it's a pointless no-op that doesn't > really do anything besides possibly throwing an exception (e.g. if the > script didn't have write access to the current directory). Actually, it will create the file if it doesn't exist, and truncate it to zero length if it does. Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details -- http://mail.python.org/mailman/listinfo/python-list
Re: sqlite savepoint problem [solved]
On Fri, 2010-03-12 at 09:35 +0100, Laszlo Nagy wrote: > > No it doesn't. The problem is that using a connection as a context > > manager doesn't do what you think. > > > > It does *not* start a new transaction on __enter__ and commit it on > > __exit__. As far as I can tell it does nothing on __enter__ and calls > > con.commit() or con.rollback() on exit. With isolation_level=None, > > these are no-ops. > > > Thank you Ryan! You are abolutely right, and thank you for reading the > source. Now everything works as I imagined. No problemo - isolation_level has given me my fair share of headaches in the past, so I couldn't resist the opportunity to understand it a little better. > The way the context manager and isolation_level works looks very very > strange to me. Here is a demonstration: > > import sqlite3 > def getconn(): > conn = sqlite3.connect(':memory:') > conn.isolation_level = None > return conn > def main(): > with getconn() as conn: > conn.execute("create table a ( i integer ) ") > try: > conn.execute("insert into a values (1)") > with conn: > conn.execute("insert into a values (2)") > raise Exception > except: > print "There was an error" > for row in conn.execute("select * from a"): > print row > main() > > > Output: > > There was an error > (1,) > (2,) > > > Looks like the context manager did not roll back anything. Yes, because there were no transactions created so there was nothing to roll back. > If I remove > isolation_level=None then I get this: > > There was an error > > E.g. the context manager rolled back something that was executed outside > the context. Yes, because the transactions created by the default isolation level do not nest, so the rollback happens at outermost scope. > I cannot argue with the implementation - it is that way. > But this is not what I would expect. I believe I'm not alone with this. That's at least two of us :-) > Just for clarity, we should put a comment at the end of the > documentation here: > > http://docs.python.org/library/sqlite3.html#sqlite3-controlling-transactions > > I would add at least these things: > > #1. By using isolation_level = None, connection objects (used as a > context manager) WON'T automatically commit or rollback transactions. > #2. Using any isolation level, connection objects WON'T automatically > begin a transaction. > #3. Possibly, include your connection manager class code, to show how to > do it "the expected" way. > > Also one should clarify in the documentation, what isolation_level does. > Looks like setting isolation_level to None is not really an "auto commit > mode". It is not even part of sqlite itself. It is part of the python > extension. I think of it as almost the opposite - you have to set isolation_level=None to get the unadulterated behaviour of the underlying sqlite library. I'm sure the devs would appreciate a documentation patch (submission details at http://python.org/dev/patches/). I'm also pretty confident that I won't have time to do one up anytime soon :-) Good luck with your project! Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: sqlite savepoint problem
On Fri, 2010-03-12 at 08:32 +0100, Laszlo Nagy wrote: > > From memory you can't issue a "CREATE TABLE" statement inside a > > transaction, at least not at the default isolation level. Such a > > statement will automatically commit the current transaction. Doesn't > > help with your current problem but worth pointing out :-) > > > Thank you. I'll keep in mind. > > When debugging strange transaction behaviour, I find it easiest to > > create the connection with isolation_level=None so that are no implicit > > transactions being created behind your back. Not sure why, but setting > > this makes your example work for me. > > > Yes, same for me. But setting it to None means auto commit mode! See here: > > http://docs.python.org/library/sqlite3.html#sqlite3-controlling-transactions > > > But it does not work that way. Look at this example > > import sqlite3 > > conn = sqlite3.connect(':memory:') > conn.isolation_level = None > with conn: > conn.execute("create table a ( i integer ) ") > > with conn: > conn.execute("insert into a values (1)") > conn.execute("SAVEPOINT sp1") > conn.execute("insert into a values (2)") > conn.execute("SAVEPOINT sp2") > conn.execute("insert into a values (3)") > conn.execute("ROLLBACK TO sp2") > conn.execute("insert into a values (4)") > conn.execute("RELEASE sp1") > > with conn: > for row in conn.execute("select * from a"): > print row > > > It prints: > > (1,) > (2,) > (4,) > > So everything is working. Nothing is auto commited. But if I change it > to "DEFERRED" or "IMMEDIATE" or "EXCLUSIVE" then it won't work. Why? I have a theory, based on a quick perusal of the sqlite3 bindings source. The bindings think that "SAVEPOINT sp1" is a "non-DML, non-query" statement. So when isolation_level is something other than None, this statement implicitly commits the current transaction and throws away your savepoints! Annotating your example: # entering this context actually does nothing with conn: # a transaction is magically created before this statement conn.execute("insert into a values (1)") # and is implicitly committed before this statement conn.execute("SAVEPOINT sp1") # a new transaction is magically created conn.execute("insert into a values (2)") # and committed, discarding the first savepoint. conn.execute("SAVEPOINT sp2") # a new transaction is magically created conn.execute("insert into a values (3)") # and committed, discarding the very savepoint we are trying to use. conn.execute("ROLLBACK TO sp2") conn.execute("insert into a values (4)") conn.execute("RELEASE sp1") In your previous multi-threaded example, try adding a "SAVEPOINT sp1" statement after deleting the rows in Thread2. You'll see that the delete is immediately committed and the rows cannot be read back by Thread1. (modified version attached for convenience). Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details import os import sqlite3 import threading import time FPATH = '/tmp/test.sqlite' if os.path.isfile(FPATH): os.unlink(FPATH) class MyConn(sqlite3.Connection): def __enter__(self): self.execute("BEGIN") return self def __exit__(self,exc_type,exc_info,traceback): if exc_type is None: self.execute("COMMIT") else: self.execute("ROLLBACK") def getconn(): global FPATH conn = sqlite3.connect(FPATH)#,factory=MyConn) conn.isolation_level = None return conn class Thr1(threading.Thread): def run(self): conn = getconn() print "Thr1: Inserting 0,1,2,3,4,5" with conn: for i in range(6): conn.execute("insert into a values (?)",[i]) print "Thr1: Commited" with conn: print "Thr1: Selecting all rows:" for row in conn.execute("select * from a"): print row print "Thr1: Wait some..." time.sleep(3) print "Thr1: Selecting again, in the same transaction" for row in conn.execute("select * from a"): print row class Thr2(threading.Thread): def run(self): conn = getconn() with conn: prin
Re: sqlite savepoint problem
On Fri, 2010-03-12 at 08:48 +0100, Laszlo Nagy wrote: > > > > I'm now confused. Also, I could not find anything about these > > isolation levels on the sqlite website. The only think I could find is > > "PRAGMA read_uncommited". If that is the same as setting > > isolation_level to None, then I don't want it. > Yes, it is. Here is a test: No it isn't. The "magic" behind isolation_level is a creation of the python sqlite bindings. You can probably tell that I'm not a fan of it. > import os > import sqlite3 > import threading > import time > > FPATH = '/tmp/test.sqlite' > if os.path.isfile(FPATH): > os.unlink(FPATH) > > def getconn(): > global FPATH > conn = sqlite3.connect(FPATH) > conn.isolation_level = None > return conn > > class Thr1(threading.Thread): > def run(self): > conn = getconn() > print "Thr1: Inserting 0,1,2,3,4,5" > with conn: > for i in range(6): > conn.execute("insert into a values (?)",[i]) > print "Thr1: Commited" > with conn: > print "Thr1: Selecting all rows:" > for row in conn.execute("select * from a"): > print row > print "Thr1: Wait some..." > time.sleep(3) > print "Thr1: Selecting again, in the same transaction" > for row in conn.execute("select * from a"): > print row > > > class Thr2(threading.Thread): > def run(self): > conn = getconn() > with conn: > print "Thr2: deleting all rows from a" > conn.execute("delete from a") > print "Thr2: Now we wait some BEFORE commiting changes." > time.sleep(3) > print "Thr2: Will roll back!" > raise Exception > > > def main(): > with getconn() as conn: > conn.execute("create table a ( i integer ) ") > thr1 = Thr1() > thr1.start() > time.sleep(1) > thr1 = Thr2() > thr1.start() > > main() > > > And the test result: > > Thr1: Inserting 0,1,2,3,4,5 > Thr1: Commited > Thr1: Selecting all rows: > (0,) > (1,) > (2,) > (3,) > (4,) > (5,) > Thr1: Wait some... > Thr2: deleting all rows from a > Thr2: Now we wait some BEFORE commiting changes. > Thr1: Selecting again, in the same transaction > Thr2: Will roll back! > Exception in thread Thread-2: > Traceback (most recent call last): > File "/usr/lib/python2.6/threading.py", line 525, in __bootstrap_inner > self.run() > File "test.py", line 44, in run > raise Exception > Exception > > > It means that setting isolation_level to None will really allow > uncommited changes to be read by other transactions! This is sad, and of > course this is something that I do not want. No it doesn't. The problem is that using a connection as a context manager doesn't do what you think. It does *not* start a new transaction on __enter__ and commit it on __exit__. As far as I can tell it does nothing on __enter__ and calls con.commit() or con.rollback() on exit. With isolation_level=None, these are no-ops. If you create your own connection wrapper that explicitly creates and commits transactions, you example will work fine with isolation_level=None. Here's the relevant changes: class MyConn(sqlite3.Connection): def __enter__(self): self.execute("BEGIN") return self def __exit__(self,exc_type,exc_info,traceback): if exc_type is None: self.execute("COMMIT") else: self.execute("ROLLBACK") def getconn(): global FPATH conn = sqlite3.connect(FPATH,factory=MyConn) conn.isolation_level = None return conn Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: sqlite savepoint problem (was: Re: sqlite3 is sqlite 2?)
On Fri, 2010-03-12 at 07:46 +0100, Laszlo Nagy wrote: > > > >>> import sqlite3 > >>> conn = sqlite3.connect(':memory:') > >>> with conn: > ... conn.execute("BEGIN") > ... conn.execute("create table a ( i integer)") > ... conn.execute("insert into a values (1)") > ... conn.execute("savepoint sp1") > ... conn.execute("insert into a values(2)") > ... conn.execute("release sp1") > ... conn.execute("COMMIT") > ... > > > > > > Traceback (most recent call last): > File "", line 7, in > sqlite3.OperationalError: no such savepoint: sp1 > >>> > > The syntax is correct: http://www.sqlite.org/lang_savepoint.html > The savepoint was really created. > But I get this error, telling "no such savepoint". What is wrong here? > Maybe it has to do something with transaction isolation? :-s From memory you can't issue a "CREATE TABLE" statement inside a transaction, at least not at the default isolation level. Such a statement will automatically commit the current transaction. Doesn't help with your current problem but worth pointing out :-) When debugging strange transaction behaviour, I find it easiest to create the connection with isolation_level=None so that are no implicit transactions being created behind your back. Not sure why, but setting this makes your example work for me. Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: sqlite3 is sqlite 2?
On Fri, 2010-03-12 at 06:48 +0100, Laszlo Nagy wrote: > gand...@ubuntu:~$ python > Python 2.6.2 (release26-maint, Apr 19 2009, 01:56:41) > [GCC 4.3.3] on linux2 > Type "help", "copyright", "credits" or "license" for more information. > >>> import sqlite3 > >>> sqlite3.version > '2.4.1' > > Is it possible to install a real sqlite version 3 somehow? I really need > it because I have to use savepoint/rollback to. That is only supported > from sqlite 3.6.8. Is it enough if I upgrade to Ubuntu Karmic? I know > that is not a question about Python itself. That's the sqlite *bindings* version: >>> sqlite3.version '2.4.1' >>> sqlite3.sqlite_version '3.6.16' >>> So this is "pysqlite" version 2.4.1, which wraps sqlite version 3.6.16. Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Upgrading Py2exe App
On Wed, 2010-02-24 at 15:05 -0800, Aahz wrote: > In article , > Ryan Kelly wrote: > > > >Yes. The idea of having a "bootstrapping exe" is that actual > >application code can be swapped out without having to overwrite the > >executable file. As long as you don't change python versions, this > >allows updates to be safe against system crashes, even on platforms > >without atomic file replacement. > > > >So the frozen app does this in a background thread: > > > > Esky(sys.executable,"http://my.updates.com";).auto_update() > > > >And it hits the given url, grabs the latest zipfile, downloads and > >unpacks and atomically places it into the application directory. Et > >viola, your app is at the latest version. > > How does this work with a running app? What if the app is a service? The changes will only take effect the next time the app is started - currently there's no support for "hot upgrading" a running app. Would definitely be an interesting feature though... Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
ANN: esky v0.4.0 [was Re: Upgrading Py2exe App]
Hi All, As promised I have made a new release of esky, my auto-update framework for frozen python apps. Details below for those who are interested. Cheers, Ryan --- esky: keep frozen apps fresh Esky is an auto-update framework for frozen Python applications. It provides a simple API through which apps can find, fetch and install updates, and a bootstrapping mechanism that keeps the app safe in the face of failed or partial updates. Esky is currently capable of freezing apps with bbfreeze, cxfreeze and py2exe. Support for py2app is in the works. The latest version is v0.4.0, with the following major changes: * added support for freezing with cx_Freeze. * improved support for freezing with py2exe. * added ability to set the icon on each executable (if the chosen freezer module supports it) * made Esky.cleanup() catch and ignore common errors. * added support for Python 3 (via distribute's "use_2to3" flag) * added a brief tutorial and example application * some backwards-incompatible API changes (see ChangeLog for details) Downloads: http://pypi.python.org/pypi/esky/0.4.0/ Code, bugs, etc: http://github.com/rfk/esky/ Tutorial: http://github.com/rfk/esky/tree/master/tutorial/ -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Overcoming python performance penalty for multicore CPU
On Sun, 2010-02-21 at 23:05 +0100, Martin v. Loewis wrote: > > It's far from scientific, but I've seen behaviour that's close to a 100% > > performance penalty on a dual-core linux system: > > > >http://www.rfk.id.au/blog/entry/a-gil-adventure-threading2 > > > > Short story: a particular test suite of mine used to run in around 25 > > seconds, but a bit of ctypes magic to set thread affinity dropped the > > running time to under 13 seconds. > > Indeed, it's not scientific - but with a few more details, you could > improve it quite a lot: what specific Linux distribution (the posting > doesn't even say it's Linux), what specific Python version had you been > using? (less important) what CPUs? If you can: what specific test suite? I'm on Ubuntu Karmic, Python 2.6.4, an AMD Athlon 7750 dual core. Unfortunately the test suite is for a proprietary application. I've been able to reproduce similar behaviour with an open-source test suite, using the current trunk of the "pyfilesystem" project: http://code.google.com/p/pyfilesystem/ In this project "OSFS" is an object-oriented interface to the local filesystem. The test case "TestOSFS.test_cases_in_separate_dirs" runs three theads, each doing a bunch of IO in a different directory. Running the tests normally: r...@durian:/storage/software/fs$ nosetests fs/tests/test_fs.py:TestOSFS.test_cases_in_separate_dirs . -- Ran 1 test in 9.787s That's the best result from five runs - I saw it go as high as 12 seconds. Watching it in top, I see CPU usage at around 150%. Now using threading2 to set the process cpu affinity at the start of the test run: r...@durian:/storage/software/fs$ nosetests fs/tests/test_fs.py:TestOSFS.test_cases_in_separate_dirs . -- Ran 1 test in 3.792s Again, best of five. The variability in times here is much lower - I never saw it go above 4 seconds. CPU usage is consistently 100%. Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Overcoming python performance penalty for multicore CPU
On Sun, 2010-02-21 at 22:22 +0100, Martin v. Loewis wrote: > John Nagle wrote: > >I know there's a performance penalty for running Python on a > > multicore CPU, but how bad is it? I've read the key paper > > ("www.dabeaz.com/python/GIL.pdf"), of course. It would be adequate > > if the GIL just limited Python to running on one CPU at a time, > > but it's worse than that; there's excessive overhead due to > > a lame locking implementation. Running CPU-bound multithreaded > > code on a dual-core CPU runs HALF AS FAST as on a single-core > > CPU, according to Beasley. > > I couldn't reproduce these results on Linux. Not sure what "HALF AS > FAST" is; I suppose it means "it runs TWICE AS LONG" - this is what I > couldn't reproduce. > > If I run Beazley's program on Linux 2.6.26, on a 4 processor Xeon (3GHz) > machine, I get 30s for the sequential execution, 40s for the > multi-threaded case, and 32s for the multi-threaded case when pinning > the Python process to a single CPU (using taskset(1)). > > So it's 6% overhead for threading, and 25% penalty for multicore CPUs - > far from the 100% you seem to expect. It's far from scientific, but I've seen behaviour that's close to a 100% performance penalty on a dual-core linux system: http://www.rfk.id.au/blog/entry/a-gil-adventure-threading2 Short story: a particular test suite of mine used to run in around 25 seconds, but a bit of ctypes magic to set thread affinity dropped the running time to under 13 seconds. Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Is there a way to continue after an exception ?
On Sun, 2010-02-21 at 13:17 +1100, Lie Ryan wrote: > On 02/21/10 12:02, Stef Mientki wrote: > > On 21-02-2010 01:21, Lie Ryan wrote: > >>> On Sun, Feb 21, 2010 at 12:52 AM, Stef Mientki > wrote: > >>> > >>>> hello, > >>>> > >>>> I would like my program to continue on the next line after an uncaught > >>>> exception, > >>>> is that possible ? > >>>> > >>>> thanks > >>>> Stef Mientki > >>>> > >>>> > >> That reminds me of VB's "On Error Resume Next" > >> > > I think that's what I'm after ... > > A much better approach is to use callbacks, the callbacks determines > whether to raise an exception or continue execution: > > def handler(e): > if datetime.datetime.now() >= datetime.datetime(2012, 12, 21): > raise Exception('The world has ended') > # else: ignore, it's fine > > def add_ten_error_if_zero(args, handler): > if args == 0: > handler(args) > return args + 10 > > print add_ten_error_if_zero(0, handler) > print add_ten_error_if_zero(10, handler) > print add_ten_error_if_zero(0, lambda e: None) # always succeeds Or if you don't like having to explicitly manage callbacks, you can try the "withrestart" module: http://pypi.python.org/pypi/withrestart/ It tries to pinch some of the good ideas from Common Lisp's error-handling system. from withrestart import * def add_ten_error_if_zero(n): # This gives calling code the option to ignore # the error, or raise a different one. with restarts(skip,raise_error): if n == 0: raise ValueError return n + 10 # This will raise ValueError print add_ten_error_if_zero(0) # This will print 10 with Handler(ValueError,"skip"): print add_ten_error_if_zero(0) # This will exit the python interpreter with Handler(ValueError,"raise_error",SystemExit): print add_ten_error_if_zero(0) Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Upgrading Py2exe App
On Fri, 2010-02-19 at 11:08 -0800, T wrote: > On Feb 18, 7:19 pm, Ryan Kelly wrote: > > On Thu, 2010-02-18 at 07:46 -0800, T wrote: > > > I have a Python app which I converted to an EXE (all files separate; > > > single EXE didn't work properly) via py2exe - I plan on distributing > > > this and would like the ability to remotely upgrade the program (for > > > example, via HTTP/HTTPS). Looks like it's not just the EXE that I > > > will need need to replace (DLLs, the library.zip, etc.). What would > > > be the best way to go about doing this? > > > > I've been working on an auto-update framework for my own frozen apps, > > you might find it useful: > > > > http://pypi.python.org/pypi/esky > > > > Docs are a little scarce at the moment, the next release will hopefully > > come with a short tutorial (as well as support for cx_freeze and maybe > > py2app, depending on how adventurous I'm feeling). > > > Thanks Ryan..this looks like it could be what I'm looking for, but I'm > still a bit unsure of how exactly how it works. Do you happen to have > an idea approx when the next release w/ tutorial will be out? If I punt on the py2app support, I should be able to get it done in the next 3-4 days. I'll send a quick email to python-list when it's ready. Here's a rough roadmap of where the project is heading: v0.4.0: cx_freeze support and a tutorial [the next 3-4 days] v0.4.1: py2app support [the next 2-3 weeks] v0.5.0: differential updates using bsdiff [next few months] Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Upgrading Py2exe App
On Thu, 2010-02-18 at 20:32 -0800, CM wrote: > On Feb 18, 7:19 pm, Ryan Kelly wrote: > > On Thu, 2010-02-18 at 07:46 -0800, T wrote: > > > I have a Python app which I converted to an EXE (all files separate; > > > single EXE didn't work properly) via py2exe - I plan on distributing > > > this and would like the ability to remotely upgrade the program (for > > > example, via HTTP/HTTPS). Looks like it's not just the EXE that I > > > will need need to replace (DLLs, the library.zip, etc.). What would > > > be the best way to go about doing this? > > > > I've been working on an auto-update framework for my own frozen apps, > > you might find it useful: > > > > http://pypi.python.org/pypi/esky > > > > > This looks pretty interesting and useful. Thanks :-) > Just to help me understand it a bit more: what is it that users will > download from some web page in order to initially get the py2exe'd app > on their system? Is it "really" an "esky", with the app's .exe file > inside it (but the esky is named the same as the app)? Currently, it's just a zip file with the frozen app in it, which the user unzips to wherever they want the app. When unzipped it looks like this: myapp.exe <-- actually the esky bootstrap exe myapp-X.Y.Z.win32/ myapp.exe <-- the actual frozen app as produced by py2exe python26.dll ...etc... This could easily be wrapped in an installer - the important thing is just that the files end up on the user's machine in the expected directory structure. > And then when > they want to update, the app's code calls the esky class to do the > work of swapping out the appropriate .exe file? Something like this? Yes. The idea of having a "bootstrapping exe" is that actual application code can be swapped out without having to overwrite the executable file. As long as you don't change python versions, this allows updates to be safe against system crashes, even on platforms without atomic file replacement. So the frozen app does this in a background thread: Esky(sys.executable,"http://my.updates.com";).auto_update() And it hits the given url, grabs the latest zipfile, downloads and unpacks and atomically places it into the application directory. Et viola, your app is at the latest version. From the packager's point of view, you run the "bdist_esky" distutils command to generate the zipfile containing your latest version, then simply upload it to your server. > Would this also work if one used InnoSetup to install the exe on the > user's system? Yes, absolutely - in fact I plan to do this myself at some stage. All that's required is that the files end up in the expected directory structure. Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Upgrading Py2exe App
On Thu, 2010-02-18 at 07:46 -0800, T wrote: > I have a Python app which I converted to an EXE (all files separate; > single EXE didn't work properly) via py2exe - I plan on distributing > this and would like the ability to remotely upgrade the program (for > example, via HTTP/HTTPS). Looks like it's not just the EXE that I > will need need to replace (DLLs, the library.zip, etc.). What would > be the best way to go about doing this? I've been working on an auto-update framework for my own frozen apps, you might find it useful: http://pypi.python.org/pypi/esky Docs are a little scarce at the moment, the next release will hopefully come with a short tutorial (as well as support for cx_freeze and maybe py2app, depending on how adventurous I'm feeling). Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Python's Reference And Internal Model Of Computing Languages
> On Tue, 2010-02-02 at 17:28 -0800, Xah Lee wrote: I know, I know, do not feed the trolls. But this is just so *wrong* that I can't help myself. > In Python, there are 2 ways to clear a hash: No, no there's not. There's one way to clear a hash and there's one way to assign a new object to a variable. > âmyHash = {}â and > âmyHash.clear()â. What is the difference? > The difference is that âmyHash={}â simply creates a new empty hash and > assigns to myHash, while âmyHash.clear()â actually clear the hash the > myHash is pointing to. > > What does that mean?? Here's a code that illustrates: > > # python > # 2 ways to clear hash and their difference > aa = {'a':3, 'b':4} > bb = aa > aa = {} > print bb # prints {'a': 3, 'b': 4} > > aa = {'a':3, 'b':4} > bb = aa > aa.clear() > print bb # prints {} > > This is like this because of the âreferenceâ concept. ...snip inane babble... > Languages that do not have any âreferenceâ or âobjectâ, or otherwise > does not require the programer to have some internal model of source > code, are: Mathematica, JavaScript, PHP. (others may include TCL, > possibly assembly langs.) Just so we're all clear exactly how much thought has gone into this little rant, here's a transcript from a JavaScript session: var aa = {}; var bb = aa; aa.hello = "world"; alert(bb.hello) --> "world" delete bb.hello alert(aa.hello) --> "undefined" OMFG, references!! Come to think of it, the JavaScript and Python object models are really very similar. I'm genuinely curious now - what little sprinkle of magic fairy dust has earned JavaScript objects the Xah Lee seal of approval while Python objects miss out? Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Why this error message
On Sun, 2010-01-31 at 15:25 -0500, Ray Holt wrote: > Why am I getting the error that test is not defined. Thanks, Ray > class SpecialFile: > def __init__(self, fileName): > self.__file = open(fileName, 'W') > self.__file.write('* Start Special File *\n\n') > def write(self, str): > self.__file.write(str) > def writelines(self, strList): > self.__file.writelines(strList) > > def __del__(self): # Destructor method, __del__. > print "entered __del__" > self.close() > > def close(self): # Clean up method > if self.__file: > self.__file.write('\\n* End Special File *') > self.__file.close() > self.__file = None > > def test(): > f = SpecialFile('testfile') > f.write('11\n') > f.close() > test() > Traceback (most recent call last): > File "C:\Python26\Classes_and_OOP_Programing.py", line 145, in > > test() > NameError: name 'test' is not defined Based on the indentation, it looks like you've defined "test" as a method on the SpecialFile class. Try dedenting it to begin in the first column. Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: shouldn't list comprehension be faster than for loops?
> > Tenting the time spent by each approach (using time.clock()), with a > > file with about 100,000 entries, I get 0.03s for the loop and 0.05s > > for the listcomp. > > Anything else being equal, list comprehensions will be the faster > becuase they incur fewer name and attribute lookups. It will be the > same as the difference between a for loop and a call to map. A list > comprehension is basically an enhancement of map. Not so. If you use the "dis" module to peek at the bytecode generated for a list comprehension, you'll see it's very similar to that generated for an explicit for-loop. The byte-code for a call to map is very different. Basically: both a for-loop and a list-comp do the looping in python bytecode, while a call to map will do the actual looping in C. >>> def comper(): ... return [i*2 for i in xrange(10)] ... >>> >>> dis.dis(comper) 2 0 BUILD_LIST 0 3 DUP_TOP 4 STORE_FAST 0 (_[1]) 7 LOAD_GLOBAL 0 (xrange) 10 LOAD_CONST 1 (10) 13 CALL_FUNCTION1 16 GET_ITER >> 17 FOR_ITER17 (to 37) 20 STORE_FAST 1 (i) 23 LOAD_FAST0 (_[1]) 26 LOAD_FAST1 (i) 29 LOAD_CONST 2 (2) 32 BINARY_MULTIPLY 33 LIST_APPEND 34 JUMP_ABSOLUTE 17 >> 37 DELETE_FAST 0 (_[1]) 40 RETURN_VALUE >>> >>> >>> >>> def maper(): ... return map(lambda i: i*2,xrange(10)) ... >>> dis.dis(maper) 2 0 LOAD_GLOBAL 0 (map) 3 LOAD_CONST 1 (>> Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: ANN: withrestart 0.2.1
On Fri, 2009-12-18 at 07:12 -0500, Neal Becker wrote: > I haven't tried it, but it sounds really cool. I suppose I should expect a > lot more overhead compared to try/except, since it's not built-in to python? It's a pretty thin layer on top of try/except so I'll be surprised if there is *too* much overhead. The only overhead is at establishment and/or invocation time - calling some extra functions, walking a few stack frames, etc. I've attached a highly scientific benchmark I threw together this morning. Results: Establishing a restart/tryexcept but not using it: test_tryexcept0: 1.23 usec test_restarts0: 34.90 usec Establishing a restart/tryexcept, returning a new value: test_tryexcept1: 3.56 usec test_restarts1: 67.30 usec Establishing a restart/tryexcept, raising a new error: test_tryexcept2: 5.86 usec test_restarts2: 90.20 usec Not having to pass status flags or callback functions through every layer of your API to properly recover from errors: tryexcept:impossible :-( withrestart: priceless :-) Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details from withrestart import * def test_tryexcept0(): def raiser(): return 7 def invoker(): return raiser() def catcher(): try: return invoker() except ValueError: return 7 assert catcher() == 7 def test_tryexcept1(): def raiser(): raise ValueError def invoker(): return raiser() def catcher(): try: return invoker() except ValueError: return 7 assert catcher() == 7 def test_tryexcept2(): def raiser(): raise ValueError def invoker(): raiser() def catcher(): try: invoker() except ValueError: raise TypeError try: catcher() except TypeError: pass else: raise AssertionError def test_restarts0(): def raiser(): return 7 def invoker(): with restarts(use_value) as invoke: return invoke(raiser) def catcher(): with Handler(ValueError,"use_value",7): return invoker() assert catcher() == 7 def test_restarts1(): def raiser(): raise ValueError def invoker(): with restarts(use_value) as invoke: return invoke(raiser) def catcher(): with Handler(ValueError,"use_value",7): return invoker() assert catcher() == 7 def test_restarts2(): def raiser(): raise ValueError def invoker(): with restarts(raise_error) as invoke: invoke(raiser) def catcher(): with Handler(ValueError,"raise_error",TypeError): invoker() try: catcher() except TypeError: pass else: raise AssertionError signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
ANN: withrestart 0.2.1
Hi All, Apologies if you receive multiple copies of this, my python-announce posts don't seem to be making it through. I've just released a new python module called "withrestart". It's an attempted Pythonisation of the restart-based condition system of Common Lisp. Details are on PyPI: http://pypi.python.org/pypi/withrestart/0.2.1 For an introduction to conditions and restarts, see "Beyond Exception Handling" by Peter Seibel: http://www.gigamonkeys.com/book/beyond-exception-handling-conditions-and-restarts.html For a quick demo of the module in action, keep reading... Cheers, Ryan About withrestart: -- Version: 0.2.1 Licence: MIT Source: http://github.com/rfk/withrestart withrestart is a Pythonisation (Lispers might rightly say "bastardisation") of the restart-based condition system of Common Lisp. It's designed to make error recovery simpler and easier by removing the assumption that unhandled errors must be fatal. A "restart" represents a named strategy for resuming execution of a function after the occurrence of an error. At any point during its execution a function can push a Restart object onto its call stack. If an exception occurs within the scope of that Restart, code higher-up in the call chain can invoke it to recover from the error and let the function continue execution. By providing several restarts, functions can offer several different strategies for recovering from errors. A "handler" represents a higher-level strategy for dealing with the occurrence of an error. It is conceptually similar to an "except" clause, in that one establishes a suite of Handler objects to be invoked if an error occurs during the execution of some code. There is, however, a crucial difference: handlers are executed without unwinding the call stack. They thus have the opportunity to take corrective action and then resume execution of whatever function raised the error. As an example, here's a function that doesn't like the number seven: def anything_but_seven(v): if v == 7: raise ValueError("Argh! A Seven!") return v And here's a function that can recover from the occurrence of a seven using the pre-defined restarts "skip" and "use_value": def sum_items(items): total = 0 for i in items: with restarts(skip,use_value) as invoke: total += invoke(anything_but_seven,i) return total Naively calling this will raise a ValueError: >>> sum_items(range(8)) Traceback (most recent call last): ... ValueError: Argh! A Seven! >>> But if we handle ValueErrors by invoking the "skip" restart, we can still get the sum of the remaining items: >>> with Handler(ValueError,"skip"): ... sum_items(range(8)) ... 21 >>> Alternately, we can invoke the "use_value" restart to replace the sevens with another value: >>> with Handler(ValueError,"use_value",12): ... sum_items(range(8)) ... 33 >>> By splitting the responsibility for error recovery between Handlers and Restarts, we can cleanly separate the low-level mechanics of recovering from an error from the high-level decisions about what sort of recovery to perform. -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: ANN: esky 0.2.1
> >> Recently I was looking into distribution mechanisms, and I passed over > >> bbfreeze because I saw no indication that Python 2.6 was supported. > > > >Not sure if it's officially supported, but I do most of my development > >on Python 2.6 and bbfreeze hasn't given me any problems as yet. > > Also, bbfreeze doesn't seem to have active development. It's slow but certainly active. Development was recently moved to github with almost no fanfare (in fact I only discovered the github site by accident): http://github.com/schmir/bbfreeze Out of curiosity, what freezer package did you settle on in the end? I'm curious it see if esky could easily switch between different freezers (although it currently depends on some rather deep details of the bbfreeze format). Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: ANN: esky 0.2.1
> >Esky is an auto-update framework for frozen python apps, built on top of > >bbfreeze. It provides a simple API through which apps can find, fetch > >and install updates, and a bootstrapping mechanism that keeps the app > >safe in the face of failed or partial updates. > > Recently I was looking into distribution mechanisms, and I passed over > bbfreeze because I saw no indication that Python 2.6 was supported. Not sure if it's officially supported, but I do most of my development on Python 2.6 and bbfreeze hasn't given me any problems as yet. Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
ANN: esky 0.2.1
I'm pleased to announce the latest release of esky, a tool for keeping your frozen apps fresh: Downloads:http://pypi.python.org/pypi/esky/ Latest Version: 0.2.1 License: BSD Esky is an auto-update framework for frozen python apps, built on top of bbfreeze. It provides a simple API through which apps can find, fetch and install updates, and a bootstrapping mechanism that keeps the app safe in the face of failed or partial updates. A frozen app that wants to auto-update itself might run the following in a background thread: if hasattr(sys,"frozen"): app = esky.Esky(sys.executable,"http://myapp.com/downloads/";) new_version = app.find_update() if new_version is not None: app.install_update(new_version) The new version of the application is linked into the app directory in the safest possible manner: using a carefully-ordered sequence of atomic renames on POSIX, using MoveFileTransacted on Windows Vista or later, and using the "rename-and-pray" method on older versions of Windows. Failed or partial updates are detected and cleaned up automatically. Enjoy! Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: comparing alternatives to py2exe
> Recently I put together this incomplete comparison chart in an attempt > to choose between the different alternatives to py2exe: > > http://spreadsheets.google.com/pub?key=tZ42hjaRunvkObFq0bKxVdg&output=html > > ...snip... > > Are there major things I'm missing or misunderstanding? A quick note - although I haven't tried it out, the latest version of bbfreeze claims to support OSX. Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: recommendation for webapp testing?
> >I need to do some basic website testing (log into account, add item to > >cart, fill out and submit forms, check out, etc.). What modules would > >be good to use for webapp testing like this? > > Windmill is an option, but I haven't tried it myself I'll second Windmill as an option, have had good experiences with it. The current version is a little on the slow side, but I believe there's a big new release just around the corner that contains significant performance improvements. Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Granularity of OSError
> > You can access the exception object which gives you greater detail. > > > > try: > > os.unlink(some_file) > > except OSError, e: > > print e.errno > > print e.strerror > > > > if e.errno == 2: > > pass > > else: > > raise > > I do this myself in a lot of places, almost exactly like this. It's > slightly clearer to use 'if e.errno == errno.ENOENT' in my opinion, > but, whatever. In some cases it's also more correct. While ENOENT is always 2, some error codes differ between windows and posix. In general it's better to use the constants from the errno module. Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
ANN: extprot 0.1.1
Hi All, Sorry if you get this twice, it seems to have gotten lost on its way through python-announce. I'm pleased to announce the first release of the "extprot" python module. Extprot implements a compact, efficient, extensible and language-neutral object serialisation protocol. License: MIT Downloads:http://pypi.python.org/pypi/extprot/ Source code: http://github.com/rfk/extprot/tree/master You can think of extprot as something akin to Google's protocol buffers, with a few extra bytes of serialisation overhead and a Python binding that doesn't have nearly as many rough edges. For example: * It's a stand-alone python module, packaged and distributed in the standard fashion. * It's friendly to dynamic package management tools like pip. * It works exclusively with standard Python objects. Declared a list field? It's a native list object. * You don't need to compile your protocol definitions. More on the extprot format itself is here: http://eigenclass.org/R2/writings/extprot-extensible-protocols-intro More on my motivations for this package here, if you're interested: http://www.rfk.id.au/blog/entry/new-python-module-extprot Enjoy! Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: [ANN] regobj - Pythonic object-based access to the Windows Registry
> > I've just released the results of a nice Sunday's coding, inspired by > > one too many turns at futzing around with the _winreg module. The > > "regobj" module brings a convenient and clean object-based API for > > accessing the Windows Registry. > > Sounds very interesting, Ryan. Just a couple questions about the > dictionary interface. Thanks for you interest and suggestions, a couple of quick points below. > I could see how you could map numbers to DWORD, 2.x str/3.x bytes to > binary, and 2.x unicode/3.x str to REG_SZ. But you don't document such > a translation, so it is unclear exactly what you actually do. This > would be somewhat weird in 2.x, though, where str commonly would want to > map to String rather than Binary. > > It seems almost necessary to add an explanation of whatever mapping is > presently done, to have complete documentation. I guess I just ran out of steam on the documentation front :-) Currently it maps integers to DWORD and anything else to REG_SZ. The idea of having a distinct Value class is to allow a more nuanced mapping to be developed, but I haven't got down to the details of that yet - my current application only requires REG_SZ. > Thinking more, I wonder if it is possible to create objects of type > Value to put in the dictionary to allow specification of multistring and > expandablestring Registry types, but then the dictionary name would have > to be redundant with the name attribute in the Value object. Maybe a > nameless value type could be invented, with just type and data attributes? It certainly is, using syntax like: HKCU.foo.bar["key"] = Value("%SYSTEMROOT%/mydir",type=REG_EXPAND_SZ)} Putting a nameless Value() instance in the initialisation dictionary should also work (but as you note, there's no documentation or tests for this yet...) Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Why doesn't this work ? For loop variable scoping ?
> newCylinderTempertature = newCylinderTemperature + deltaTemp Take a careful look at the variable name here: "Tempertature". Python's dynamic nature provides a lot of wonderful benefits, but you've just hit one of the drawbacks - you don't get any protection from typos in variable names. Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list
Re: Why is lambda allowed as a key in a dict?
>Python 2.5.1 (r251:54863, Oct 30 2007, 13:45:26) > [GCC 4.1.2 20070925 (Red Hat 4.1.2-33)] on linux2 > Type "help", "copyright", "credits" or "license" for more information. > >>> x = { } > >>> x[lambda arg: arg] = 5 > >>> x[lambda arg: arg] > Traceback (most recent call last): > File "", line 1, in > KeyError: at 0x2abaab18> I think the point is that function objects compare by object identity, so the two lambdas you use above are not equal even though they have the same code. Consider: >>> a = lambda arg: arg >>> x = {} >>> x[a] = 5 >>> x[a] 5 >>> x[lambda arg:arg] Traceback (most recent call last): File "", line 1, in KeyError: at 0xa06602c> >>> Cheers, Ryan -- Ryan Kelly http://www.rfk.id.au | This message is digitally signed. Please visit r...@rfk.id.au| http://www.rfk.id.au/ramblings/gpg/ for details signature.asc Description: This is a digitally signed message part -- http://mail.python.org/mailman/listinfo/python-list