第七色在线视频,2021少妇久久久久久久久久,亚洲欧洲精品成人久久av18,亚洲国产精品特色大片观看完整版,孙宇晨将参加特朗普的晚宴

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

python 3 lambda 的參數(shù)綁定似乎已損壞

python 3 lambda 的參數(shù)綁定似乎已損壞

慕娘9325324 2023-07-18 14:59:56
我在 CentOS 7 環(huán)境中使用 Python 3.6.10。我正在嘗試創(chuàng)建一個基于結(jié)構(gòu)化規(guī)范執(zhí)行的命令列表。將其視為 lambda 列表似乎很自然且符合 Python 風格。我通過遍歷規(guī)范來構(gòu)建 lambda 列表。令我驚訝的是,當我執(zhí)行結(jié)果時,我發(fā)現(xiàn)每個 lambda 都是相同的,因為它在創(chuàng)建 lambda 時沒有捕獲其參數(shù)。我認為這是一個錯誤。以下是說明該行為的示例代碼:specification = {    'labelOne': ['labelOne.one', 'labelOne.two', 'labelOne.three', 'labelOne.four', 'labelOne.five'],    'labelTwo': ['labelTwo.one', 'labelTwo.two', 'labelTwo.three', 'labelTwo.four', 'labelTwo.five'],    'labelThree': ['labelThree.one', 'labelThree.two', 'labelThree.three', 'labelThree.four', 'labelThree.five'],    'labelFour': ['labelFour.one', 'labelFour.two', 'labelFour.three', 'labelFour.four', 'labelFour.five'],    'labelFive': ['labelFive.one', 'labelFive.two', 'labelFive.three', 'labelFive.four', 'labelFive.five'],    }lambdas = []for label, labelStrings in specification.items():    for labelString in labelStrings:        lambdaString = f"""Label: \"{label}\" with labelString: \"{labelString}\""""        oneArgLambda = lambda someArg: print(someArg, lambdaString)        lambdas.append(oneArgLambda)for each in lambdas:    each('Show: ')我期望看到這個:Show:  Label: "labelOne" with labelString: "labelOne.one"Show:  Label: "labelOne" with labelString: "labelOne.two"Show:  Label: "labelOne" with labelString: "labelOne.three"Show:  Label: "labelOne" with labelString: "labelOne.four"Show:  Label: "labelOne" with labelString: "labelOne.five"Show:  Label: "labelTwo" with labelString: "labelTwo.one"Show:  Label: "labelTwo" with labelString: "labelTwo.two"Show:  Label: "labelTwo" with labelString: "labelTwo.three"Show:  Label: "labelTwo" with labelString: "labelTwo.four"lambda 的參數(shù)綁定是在執(zhí)行 lambda 時發(fā)生的,而不是在創(chuàng)建 lambda 時發(fā)生的。這至少是出乎意料的,而且我認為可以說是錯誤的。我認為 lambda 盡管有局限性,但應該創(chuàng)建一個 CLOSURE —— 它的整個目的是捕獲其參數(shù)在創(chuàng)建時的狀態(tài),以便稍后在計算 lambda 時可以使用它們。這就是為什么它被稱為“閉包”,因為它在創(chuàng)建時關(guān)閉了其參數(shù)的值。我有什么誤解嗎?
查看完整描述

3 回答

?
德瑪西亞99

TA貢獻1770條經(jīng)驗 獲得超3個贊

正如您所說,它創(chuàng)建了 CLOSURE,并且閉包在lambdaString的上部范圍中使用指定變量,但技巧是所有 lambda 都使用對lambdaString的相同引用,并且因為每次它記住最后一個時都更改它。例如:


c = ['one', 'two']

res = []


for i in range(2):

    for y in c:

        def la(x):

            print(x, y)

        res.append(la)


for la in res:

    la('Show: ')

# Show:  two

# Show:  two

# Show:  two

# Show:  two

你只需要另一個關(guān)閉來防止這種情況


c = ['one', 'two']

res = []


for i in range(2):

    for y in c:

        def closure_y(y):

            def la(x):

                print(x, y)

            return la

            

        res.append(closure_y(y))


for la in res:

    la('Show: ')

# Show:  one

# Show:  two

# Show:  one 

# Show:  two

完整代碼可能是


specification = {

    'labelOne': ['labelOne.one', 'labelOne.two', 'labelOne.three', 'labelOne.four', 'labelOne.five'],

    'labelTwo': ['labelTwo.one', 'labelTwo.two', 'labelTwo.three', 'labelTwo.four', 'labelTwo.five'],

    'labelThree': ['labelThree.one', 'labelThree.two', 'labelThree.three', 'labelThree.four', 'labelThree.five'],

    'labelFour': ['labelFour.one', 'labelFour.two', 'labelFour.three', 'labelFour.four', 'labelFour.five'],

    'labelFive': ['labelFive.one', 'labelFive.two', 'labelFive.three', 'labelFive.four', 'labelFive.five'],

    }


lambdas = []

for label, labelStrings in specification.items():

    for labelString in labelStrings:

        lambdaString = f"""Label: \"{label}\" with labelString: \"{labelString}\""""


        def clousure(lambdaString):

            oneArgLambda = lambda someArg: print(someArg, lambdaString)

            return oneArgLambda


        lambdas.append(clousure(lambdaString))


for each in lambdas:

    each('Show: ')


查看完整回答
反對 回復 2023-07-18
?
婷婷同學_

TA貢獻1844條經(jīng)驗 獲得超8個贊

您還有一些其他評論和答案來解釋正在發(fā)生的事情,并且您的問題“有趣”是因為它迫使讀者對代碼和各種綁定問題感到困惑。


但是,如果我在審查過程中從同事那里看到了您的代碼,我會要求重寫 - 不是因為我會立即知道存在錯誤,而是因為它需要太多的頭腦來思考是否來自周圍的綁定(并改變) 范圍將完全按照希望的方式運行。


相反,堅持在你的程序中實行更嚴格的紀律,從而減輕你的讀者(大多數(shù)時候誰是你)的認知負擔。具體來說,將函數(shù)創(chuàng)建移至真正隔離的范圍,并將所有不同的輸入傳遞給該函數(shù)創(chuàng)建者。這種方法是可靠的,因為它要么在第一次嘗試時起作用,要么完全失?。ㄈ绻雎詫⑺行枰膮?shù)傳遞給函數(shù)創(chuàng)建者)。


一種方法是:


# A function to create another function, with non-surprising argument binding.

# We expect nothing from the surrounding scope. All business can be done locally.

def get_func(label, x):

    return lambda prefix: print(f'''{prefix} => {label}: {x}''')


# Some input data.

specification = {

    label : [label + str(n) for n in range(3)]

    for label in ('A', 'B', 'C')

}


# Use that data to create some functions.

funcs = [

    get_func(label, x)

    for label, xs in specification.items()

    for x in xs

]


# Run 'em.

for f in funcs:

    f('Show')


查看完整回答
反對 回復 2023-07-18
?
幕布斯7119047

TA貢獻1794條經(jīng)驗 獲得超8個贊

這是一個替代方案


lambdas = []

for label, labelStrings in specification.items():

    for labelString in labelStrings:

        lambdaString = f"""Label: \"{label}\" with labelString: \"{labelString}\""""

        oneArgLambda = lambda someArg, lambdaString: print(someArg, lambdaString)

        lambdas.append((oneArgLambda, lambdaString))


for f, lambdaString in lambdas:

    f('Show: ', lambdaString)


查看完整回答
反對 回復 2023-07-18
  • 3 回答
  • 0 關(guān)注
  • 153 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯(lián)系客服咨詢優(yōu)惠詳情

幫助反饋 APP下載

慕課網(wǎng)APP
您的移動學習伙伴

公眾號

掃描二維碼
關(guān)注慕課網(wǎng)微信公眾號