Python 我是否可以以某种方式将此循环转换为映射(lambda x:…)?

Python 我是否可以以某种方式将此循环转换为映射(lambda x:…)?,python,optimization,lambda,Python,Optimization,Lambda,我正在尝试优化一种方法,该方法在从0->num # Example of how the below works, for clarity # # base => [0,1,1,2,1,2,2] # index => 7 # # {7} -- # bin(7) : 111 # bin(7-1) : 110 # 111 & 110 : 110 (6) #

我正在尝试优化一种方法,该方法在从
0->num

# Example of how the below works, for clarity
#
# base => [0,1,1,2,1,2,2]
# index => 7
#
#   {7} --
#       bin(7)              :   111
#       bin(7-1)            :   110
#       111 & 110           :   110 (6)
#       append(base[6]+1)   :   append(3)
#     //end 7
#
# base => [0,1,1,2,1,2,2,3]

def countBits(num):
    index = 1
    base = [0]

    while(index <= num):
        base.append(base[(index & (index - 1))]+1)
        index += 1

    return base
#为了清晰起见,下面的示例说明了如何工作
#
#基本=>[0,1,1,2,1,2,2]
#指数=>7
#
#   {7} --
#bin(7):111
#垃圾箱(7-1):110
#       111 & 110           :   110 (6)
#追加(基[6]+1):追加(3)
#//完7
#
#基本=>[0,1,1,2,1,2,2,3]
def计数位(num):
索引=1
基数=[0]
虽然(索引我发现了2个(功能型)解决方案,但它们几乎不“到位”。而且,可能两者都比循环工作得慢

首先,不是使用map,而是使用reduce:

def countBits2(num):
    from functools import reduce
    index = 1;
    base = reduce( lambda base, index: (base.append( base[(index & (index - 1))]+1 ), base)[1], range( 1, num+1 ), [0] )
    return base
第二个是地图:

def countBits3( num ):
    base = [0]     
    def m_append( index ):
        val = base[(index & (index - 1))]+1
        base.append( val )
        return val

    return [0] + list( map( m_append, range( 1, num+1) ) )
    #also possible to return base
    #list( map( ... ) ) # list required to force mapping on py3
    #return base
m_append
可能会被重写为lambda(与reduce尝试中的方法相同),但lambda将非常长。

我找到了2个(函数式)解决方案,但它们几乎不“到位”。而且,可能两者都会比循环运行得慢

首先,不是使用map,而是使用reduce:

def countBits2(num):
    from functools import reduce
    index = 1;
    base = reduce( lambda base, index: (base.append( base[(index & (index - 1))]+1 ), base)[1], range( 1, num+1 ), [0] )
    return base
第二个是地图:

def countBits3( num ):
    base = [0]     
    def m_append( index ):
        val = base[(index & (index - 1))]+1
        base.append( val )
        return val

    return [0] + list( map( m_append, range( 1, num+1) ) )
    #also possible to return base
    #list( map( ... ) ) # list required to force mapping on py3
    #return base

m_append
可以重写为lambda(与reduce尝试中的方法相同),但它将是非常长的lambda。

也许您想要这样的东西

num = 11

base = [0]
for _ in range(1, num):
    base.extend(map(lambda index: base[(index & (index -1))] + 1, [_]))
结果:

[0, 1, 1, 2, 1, 2, 2, 3, 1, 2, 2]

也许你想要这样的东西

num = 11

base = [0]
for _ in range(1, num):
    base.extend(map(lambda index: base[(index & (index -1))] + 1, [_]))
结果:

[0, 1, 1, 2, 1, 2, 2, 3, 1, 2, 2]

这真的有效吗?是的!刚刚更新了一条注释,解释了一个示例如果循环体引用了您要添加的内容,则很难将循环转换为列表理解或
map
表达式。
base.append(base[…])
是一个危险信号,你不容易翻译成一行。@MrDuk你可以用
map
解决这个问题,但是你不能涉及
lambda
,因为map不会修改
base
,除非它完全耗尽了它所迭代的内容。
map(lambda n:bin(n).count('1'),range(num+1))
这真的有效吗?是的!刚刚更新了一条注释,解释了一个示例如果循环体引用了您要附加的内容,则很难将循环转换为列表理解或映射表达式。
base.append(base[…])
是一个危险信号,你不容易翻译成一行。@MrDuk你可以用
map
解决这个问题,但是你不能涉及
lambda
,因为map不会修改
base
,除非它完全耗尽了它所迭代的内容。
map(lambda n:bin(n).count('1'),range(num+1))