views:

305

answers:

4

It seems that Python standard library lacks various useful concurrency-related concepts such as atomic counter, executor and others that can be found in e.g. java.util.concurrent. Are there any external libraries that would provide easier building blocks for concurrent Python applications?

+3  A: 
Hank Gay
+3  A: 

kamaelia provides tools for abstracting concurrency to threads or process etc.

Mark
+3  A: 

Although it may not be immediately obvious, itertools.count is indeed an atomic counter (the only operation on an instance x thereof, spelled next(x), is equivalent to an "atomic ++x" if C had such a concept;-). Edit: at least, this surely holds in CPython; I thought it was part of the Python standard definition but apparently IronPython and Jython disagree (not ensuring thread-safety of count.next in their current implementations) so I may well be wrong!

That is, suppose you currently have a data structure such as:

  counters = dict.fromkeys(words_of_interest, 0)
  ...
  if w in counters: counters[w] += 1

and your problem is that the latter increment is not atomic, so if two threads are at the same time dealing with the same word of interest the two increments might interfere (only one would "take", so the counter would be incremented only by one, not by two). Then:

  counters = dict((w, itertools.count()) for w in words_of_interest)
  ...
  if w in counters: next(counters[w])

will perform the same operations, but in an atomic way.

(There is unfortunately no obvious, documented way to "extract the current value of the counter", though in fact str(x) does return a string such as 'count(3)' from which the current value can be parsed out again;-).

Alex Martelli
Isn't this atomicity merely an implementation detail of CPython and the way GIL and C code work together, though?
Tuure Laurinolli
`d = defaultdict(itertools.count) \n for w in words_of_interest: next(d[w])`
J.F. Sebastian
@J.F.Sebastian, your variant isn't intrinsically "atomic" (there's quite a difference in thread-safety between **adding** a key to a dict -- including implicitly via defaultdict -- which might cause rehashing, versus strictly using only existing keys, which is what my code does). @Tuure, I just browsed the IronPython and Jython sources and it seems they agree with your interpretation -- which sounds peculiar to me, but I guess I may be wrong here -- let me edit to add a point about that!
Alex Martelli
+3  A: 

Kamaelia, as already mentioned, is aimed at making concurrency easier to work with in python.

Its original use case was network systems (which are a naturally concurrent) and developed with the viewpoint "How can we make these systems easier to develop and maintain".

Since then life has moved on and it is being used in a much wider variety of problem domains from desktop systems (like whiteboarding applications, database modelling, tools for teaching children to read and write) through to back end systems for websites (like stuff for transcoding & converting user contributed images and video for web playback in a variety of scenarios and SMS / text messaging applications.

The core concept is essentially the same idea as Unix pipelines - except instead of processes you can have python generators, threads, or processes - which are termed components. These communicate over inboxes and outboxes - as many as you like of each, rather than just stdin/stdout/stderr. Also rather than requiring serialised file interfaces, you pass between components fully fledged python objects. Also rather than being limited to pipelines, you can have arbitrary shapes - called graphlines.

You can find a full tutorial (video, slides, downloadable PDF booklet) here:

Or the 5 minute version here (O'Reilly ignite talk):

The focus on the library is pragmatic development, system safety and ease of maintenance though some effort has gone in recently towards adding some syntactic sugar. Like anything the developers (me and others :-) welcome feedback on improving it.

You can also find more information here: - http://www.slideshare.net/kamaelian

Primarily, Kamaelia's core (Axon) was written to make my day job easier, and to wrap up best practice (message passing, software transactional memory) in a reusable fashion. I hope it makes your life easier too :-)

Michael Sparks
Regarding the STM BTW - see this page for details of how to use a simplfied STM - http://www.kamaelia.org/STM. If you're familiar with version control, STM shouldn't be weird and scary even if the phrase/name may be.
Michael Sparks