Title: Pipe: Infix syntax for Python Pipe is a Python module enabling infix syntax in Python. For those asking "Why ?" let's take an example: Compare the readability of the classical prefix syntax: :::python sum(select(where(take_while(fib(), lambda x: x < 1000000) lambda x: x % 2), lambda x: x * x)) And the infix syntax: :::python fib() | take_while(lambda x: x < 1000000) \ | where(lambda x: x % 2) \ | select(lambda x: x * x) \ | sum() Isn't the infix syntax more readable? The base class of Pipe is kept simple (7 lines of python) and is usable as a decorator permitting you to create new 'pipeable' functions easily. The module provides like 30 prepared pipes functions like `where`, `group_by`, `sort`, `take_while`... A pipeable function takes an iterable (`tuple`, `list`, `generator`) and yields to be itself an iterator, so pipeable function can be piped together. Let me introduce the basic usage of the `Pipe` module, then I'll write some bits on how to build new ones: To start, get it from PyPI http://pypi.python.org/pypi/pipe/1.3 and install it, open a REPL, import pipe, and play: :::pycon Python 2.6.6 (r266:84292, Dec 26 2010, 22:31:48) [GCC 4.4.5] on linux2 Type "help", "copyright", "credits" or "license" for more information. >>> from pipe import * >>> [1, 2, 3, 4, 5] | add 15 >>> [5, 4, 3, 2, 1] | sort [1, 2, 3, 4, 5] Until here it's easy, to know more about available pipes, just read the `help(pipe)` in the REPL, all are explained with an example as a doctest Now as we know that pipeable functions use iterables, we can try to pipe together two or more pipeables: :::pycon >>> [1, 2, 3, 4, 5] | where(lambda x: x % 2) | concat '1, 3, 5' >>> [1, 2, 3, 4, 5] | where(lambda x: x % 2) | tail(2) | concat '3, 5' >>> [1, 2, 3, 4, 5] | where(lambda x: x % 2) | tail(2) | select(lambda x: x * x) | concat '9, 25' >>> [1, 2, 3, 4, 5] | where(lambda x: x % 2) | tail(2) | select(lambda x: x * x) | add 34 Now, a bit about lazyness, as Pipe use iterables, the evaluation of a whole Pipe is lazy, so we can play with infinite generators like this one : :::pycon >>> def fib(): ... a, b = 0, 1 ... while True: ... yield a ... a, b = b, a + b Now we can do every kind of stuff into the fibonacci sequence, like solving the 2nd problem of http://projecteuler.net in a readable one liner: > Find the sum of all the even-valued terms in Fibonacci which do not > exceed four million. :::pycon >>> euler2 = fib() | where(lambda x: x % 2 == 0) | take_while(lambda x: x < 4000000) | add >>> assert euler2 == 4613732 Isn't it pretty? Let now see how to create new pipeable functions using the `@pipe` decorator: You want to create a function that yields the first x elements from its input You want its usage to be `(1, 2, 3, 4, 5) | take(2)` to take the fist 2 elements. I know that you are thinking about a basic implementation like: :::python def take(iterable, qte): for item in iterable: if qte > 0: qte -= 1 yield item else: return Right? You take an iterable, a qantity, and while the quantity is not reached, you just have to yield? OK, just add `@pipe` to you take function and it's pipeable :-)