[英]Starred expression in ternary operator python
我編寫了一個 python 程序來打印字符串中最多每 3 個數字的 ascii 值,如果長度不能被三整除,則打印"ERROR"
。 當我遇到SyntaxError
時,我正在編寫代碼。
代碼:
c=input()
p=len(c)
c=[int(c[i:i+3])for i in range(0,len(c),3)]
print("ERROR"if p%3else*map(chr,c),sep='')#SyntaxError here
但這有效:
c=input()
p=len(c)
c=[int(c[i:i+3])for i in range(0,len(c),3)]
print(*map(chr,c),sep='')
在*
之前或3
之后放置一個空格是行不通的。 我可以只使用''.join
但它長了一個字符。 我的問題是為什么我不能在三元運算符中使用帶星號的表達式?
print(*(["ERROR"] if p%3 else map(chr,c)),sep="!")
保持在三元以外
因為*
必須應用於產生參數集的整個表達式,而不是它的一部分,並且不是有條件的。 在內部,CPython使用不同的字節碼進行拆包與普通調用的調用,因此您的條件將要求它根據print
的參數更改字節碼以調用print
,本質上是將您編寫的內容重寫為偽代碼,例如:
if p % 3:
call(print, "ERROR", sep='')
else:
call_varargs(print, *map(chr, c), sep='')
這超出了編譯器的能力。
如果您想完成這項工作,可以執行以下操作:
print(*(("ERROR",) if p%3 else map(chr,c)), sep='')
這樣可以確保整個三元計算結果為不可打包的序列,並對無條件生存的所有內容進行打包,從而避免了混亂。
*
擴展器將單個可枚舉變量轉換為單個變量。 例如
li = [1,2,3]
print(*li)
產生: 1 2 3
而不是[1, 2, 3]
。
一個值與多個值
它似乎刪除了括號並將單個字符串傳遞給print
,但這只是一個表象,它實際上用 3 個變量替換了單個列表變量,實際上相當於:
print(li[0], li[1], li[2])
它起作用是因為print
接受可變數字 arguments,所以在我們的例子中它可以處理單個列表或這三個整數。
條件表達式是一個單值運算符
但是,在您的代碼中,您在條件表達式中使用星號運算符:
c = '065066067068'
p = len(c)
c = [int(c[i:i+3]) for i in range(0, p, 3)]
print('ERROR' if p%3 else *map(chr, c), sep='!')
print
將能夠接受表達式的兩種評估,單個字符串值 ( 'ERROR'
) 或來自map
的多個字符值。
但是條件表達式會阻止根據條件 ( p%3
) 返回多個值。 表達式 output 必須是單個值。 因此,您別無選擇,只能將map
中的列表作為可枚舉對象返回,並僅在三元運算符之外解除嵌套,例如在print
語句中。
字符串是可枚舉的,而不是標量值
但是,此解決方案現在引入了另一個問題:取消嵌套還將常量字符串ERROR
轉換為單個字符,因為字符串被 Python 視為可枚舉的單個字符(如您所知,因為您將此屬性用於輸入字符串)。 當條件為真時,output 將是:
E!R!R!O!R
因此,必須首先將字符串轉換為可枚舉的字符串,例如元組
最終解決方案
if p%3: s = ('ERROR',)
else: s = map(chr, c)
print(*s, sep='!')
輸出將是:
A!B!C!D
ERROR
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.