python python中有没有结果的地图?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/1080026/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Is there a map without result in python?
提问by Juergen
Sometimes, I just want to execute a function for a list of entries -- eg.:
有时,我只想为条目列表执行一个函数——例如:
for x in wowList:
installWow(x, 'installed by me')
Sometimes I need this stuff for module initialization, so I don't want to have a footprint like x in global namespace. One solution would be to just use map together with lambda:
有时我需要这些东西来进行模块初始化,所以我不想在全局命名空间中有像 x 这样的足迹。一种解决方案是将 map 与 lambda 一起使用:
map(lambda x: installWow(x, 'installed by me'), wowList)
But this of course creates a nice list [None, None, ...] so my question is, if there is a similar function without a return-list -- since I just don't need it.
但这当然会创建一个不错的列表 [None, None, ...] 所以我的问题是,如果有一个没有返回列表的类似函数——因为我不需要它。
(off course I can also use _x and thus not leaving visible footprint -- but the map-solution looks so neat ...)
(当然,我也可以使用 _x,因此不会留下可见的足迹——但地图解决方案看起来很整洁......)
采纳答案by f0xdx
You can use the built-in any
function to apply a function without return statementto any item returned by a generator without creating a list. This can be achieved like this:
您可以使用内置any
函数将不带 return 语句的函数应用于生成器返回的任何项目,而无需创建列表。这可以像这样实现:
any(installWow(x, 'installed by me') for x in wowList)
I found this the most concise idom for what you want to achieve.
我发现这是您想要实现的最简洁的习惯用法。
Internally, the installWow
function does return None
which evaluates to False
in logical operations. any
basically applies an or
reduction operation to all items returned by the generator, which are all None
of course, so it has to iterate over all items returned by the generator. In the end it does return False
, but that doesn't need to bother you. The good thing is: no list is created as a side-effect.
在内部,该installWow
函数确实返回None
,其计算结果为False
逻辑运算。any
基本上or
对生成器返回的所有项目应用归约操作None
,当然这些都是,所以它必须迭代生成器返回的所有项目。最后它确实 return False
,但这不需要打扰你。好处是:没有创建列表作为副作用。
Note that this only works as long as your function returns something that evaluates to False
, e.g., None
or 0. If it does return something that evaluates to True
at some point, e.g., 1
, it will not be applied to any of the remaining elements in your iterator. To be safe, use this idiom mainly for functions without return statement.
请注意,这仅在您的函数返回计算结果为False
,例如None
或 0 的内容时才有效。如果它确实返回了True
在某个时刻计算为 的内容,例如1
,则它将不会应用于迭代器中的任何剩余元素. 为了安全起见,这个习惯用法主要用于没有 return 语句的函数。
回答by John Montgomery
You could make your own "each" function:
您可以制作自己的“每个”功能:
def each(fn, items):
for item in items:
fn(item)
# called thus
each(lambda x: installWow(x, 'installed by me'), wowList)
Basically it's just map, but without the results being returned. By using a function you'll ensure that the "item" variable doesn't leak into the current scope.
基本上它只是地图,但没有返回结果。通过使用函数,您将确保“item”变量不会泄漏到当前作用域中。
回答by RichieHindle
How about this?
这个怎么样?
for x in wowList:
installWow(x, 'installed by me')
del x
回答by Mark Rushakoff
You might try this:
你可以试试这个:
filter(lambda x: installWow(x, 'installed by me') and False, wowList)
That way, the return result is an empty list no matter what.
这样,无论如何,返回结果都是一个空列表。
Or you could just drop the and False
if you can force installWow()
to always return False
(or 0 or None
or another expression that evaluates false).
或者您可以删除and False
if 您可以强制installWow()
始终返回False
(或 0None
或其他计算结果为 false 的表达式)。
回答by balpha
Every expression evaluates to something, so you always get a result, whichever way you do it. And any such returned object (just like your list) will get thrown away afterwards because there's no reference to it anymore.
每个表达式的计算结果都是一样的,因此无论您采用哪种方式,您总是会得到一个结果。并且任何此类返回的对象(就像您的列表一样)将在之后被丢弃,因为不再引用它。
To clarify: Very few things in python are statements that don't return anything. Even a function call like
澄清一下:python 中很少有不返回任何内容的语句。甚至像这样的函数调用
doSomething()
still returns a value, even if it gets discarded right away. There is no such thing as Pascal's function / procedure distinction in python.
仍然返回一个值,即使它被立即丢弃。python中没有Pascal的函数/过程区分这样的东西。
回答by Alexander Ljungberg
You could use a filter and a function that doesn't return a True value. You'd get an empty return list since filter only adds the values which evaluates to true, which I suppose would save you some memory. Something like this:
您可以使用过滤器和不返回 True 值的函数。你会得到一个空的返回列表,因为过滤器只添加评估为真的值,我想这会为你节省一些内存。像这样的东西:
#!/usr/bin/env python
y = 0
def myfunction(x):
global y
y += x
input = (1, 2, 3, 4)
print "Filter output: %s" % repr(filter(myfunction, input))
print "Side effect result: %d" % y
Running it produces this output:
运行它会产生以下输出:
Filter output: ()
Side effect result: 10
回答by Anurag Uniyal
if it is ok to distruct wowList
如果可以破坏 wowList
while wowList: installWow(wowList.pop(), 'installed by me')
if you do want to maintain wowList
如果你确实想维护 wowList
wowListR = wowList[:]
while wowListR: installWow(wowListR.pop(), 'installed by me')
and if order matters
如果订单很重要
wowListR = wowList[:]; wowListR.reverse()
while wowListR: installWow(wowListR.pop(), 'installed by me')
Though as the solution of the puzzle I like the first :)
虽然作为谜题的解决方案,我喜欢第一个:)
回答by Anurag Uniyal
I can not resist myself to post it as separate answer
我无法抗拒自己将其作为单独的答案发布
reduce(lambda x,y: x(y, 'installed by me') , wowList, installWow)
only twist is installWow should return itself e.g.
唯一的扭曲是 installWow 应该返回自身,例如
def installWow(*args):
print args
return installWow
回答by Nick
I tested several different variants, and here are the results I got.
我测试了几种不同的变体,这是我得到的结果。
Python 2:
蟒蛇2:
>>> timeit.timeit('for x in xrange(100): L.append(x)', 'L = []')
14.9432640076
>>> timeit.timeit('[x for x in xrange(100) if L.append(x) and False]', 'L = []')
16.7011508942
>>> timeit.timeit('next((x for x in xrange(100) if L.append(x) and False), None)', 'L = []')
15.5235641003
>>> timeit.timeit('any(L.append(x) and False for x in xrange(100))', 'L = []')
20.9048290253
>>> timeit.timeit('filter(lambda x: L.append(x) and False, xrange(100))', 'L = []')
27.8524758816
Python 3:
蟒蛇3:
>>> timeit.timeit('for x in range(100): L.append(x)', 'L = []')
13.719769178002025
>>> timeit.timeit('[x for x in range(100) if L.append(x) and False]', 'L = []')
15.041426660001889
>>> timeit.timeit('next((x for x in range(100) if L.append(x) and False), None)', 'L = []')
15.448063717998593
>>> timeit.timeit('any(L.append(x) and False for x in range(100))', 'L = []')
22.087335471998813
>>> timeit.timeit('next(filter(lambda x: L.append(x) and False, range(100)), None)', 'L = []')
36.72446593800123
Note that the time values are not that precise (for example, the relative performance of the first three options varied from run to run). My conclusion is that you should just use a loop, it's more readable and performs at least as well as the alternatives. If you want to avoid polluting the namespace, just del
the variable after using it.
请注意,时间值不是那么精确(例如,前三个选项的相对性能因运行而异)。我的结论是你应该只使用一个循环,它更具可读性并且至少与替代方案一样好。如果要避免污染命名空间,只需del
使用它后的变量。
回答by benlast
If you're worried about the need to control the return value (which you need to do to use filter) and prefer a simpler solution than the reduceexample above, then consider using reducedirectly. Your function will need to take an additional first parameter, but you can ignore it, or use a lambda to discard it:
如果您担心需要控制返回值(使用filter需要这样做)并且更喜欢比上面的reduce示例更简单的解决方案,那么请考虑直接使用reduce。您的函数将需要采用额外的第一个参数,但您可以忽略它,或使用 lambda 来丢弃它:
reduce(lambda _x: installWow(_x, 'installed by me'), wowList, None)