Please describe the problem you're trying to solve. Even if Python had a
direct equivalent of "Ruby closures or blocks", which I don't think it
does, it may not be the best solution to your problem.
--
Carsten Haese
http://informixdb.sourceforge.net
Python's nameless functions are week. So it supports iterators
and generators using protocols, comprehensions and a few simple
statements, rather than promoting the use of nameless functions.
Ruby's
some_list.each do |item|
puts item
end
if I understood it correctly, In Python would be:
for item in some_list:
print item
That works for any object that supports the iterator protocol.
--
Neil Cerutti
Python isn't Ruby. Python has a lambda function for creating
anonymous functions, but many of the common use cases expired with the
introduction of iterators and comprehensions. Python's functions are
first class objects, and can be passed around, bound to names, and
used like any other object. (I don't know whether Ruby's functions
are first class objects.) Python's function objects are callable, but
so are classes (calling them creates a class instance) and some
instances (those that define the __call__ special method).
If you can't find a way of doing what you want with iterators,
comprehensions, or lambda, consider writing a little function. Heck,
you can even nest functions in Python or pass a function as a
parameter.
For example, removing all names that start with a 'J' from a list of
names:
newListOfNames = [ name for name in nameList if not
name.startswith('J') ] # List comprehension
newListOfNames = filter(lambda name: not name.startswith('J'),
nameList) # Filter with lambda
# Explicit for-loop
newListOfNames = []
for name in nameList:
if not name.startswith('J'): newListOfNames.append(name)
Take a look at "http://ivan.truemesh.com/archives/000392.html" for a
comparison between some simple Ruby code and Python. Hope this helps.
--Jason
# Generic counter
def counter(min=None, max):
if not min:
min = 0
for i in xrange(min, max):
yield i
i = i + 1
When called, this function will yield the value of i and remember its
state. The next time it's called, it will increment i, then continue
on another iteration of the loop, yielding the new value of i.
For example:
my_counter = counter(0, 10)
my_counter() # <-- 0
my_counter() # <-- 1
for i in my_counter():
print i
# Prints 2-10 (the remaining numbers in xrange(min, max))
You'd have to add a little more parameter-checking for this to work like
you intend.
/W
Inner functions allow you to define closures and (named) blocks
anywhere). Anonymous blocks must consist of a single expression.
-Mike
Uhmm, I think this won't win the Best Python Code Of The Week Award :)
Apart from the already noted syntax error in the function definition, the
`i = i + 1` is useless because `i` gets reassigned right on the next loop.
And you don't "call" a generator, you have to iterate over it;
my_counter() will raise an error. This would be the right way:
my_counter = counter(0, 10)
my_counter.next() <-- 0
my_counter.next() <-- 1
for value in my_counter:
print value <-- 2 to 9
--
Gabriel Genellina