2010-04-03 29 views
7

tôi có chức năng sau lambda:Python lambda trở về None thay vì chuỗi rỗng

f = lambda x: x == None and '' or x 

Nó sẽ trả về một chuỗi rỗng nếu nó nhận được Không như là đối số hoặc đối số nếu nó không phải là Không.

Ví dụ:

>>> f(4) 
4 
>>> f(None) 
>>> 

Nếu tôi gọi f (None) thay vì nhận được một chuỗi rỗng tôi nhận được Không. Tôi đã in kiểu hàm trả về và tôi nhận được NoneType. Tôi đã mong đợi chuỗi.

loại ('') trả về chuỗi, vì vậy tôi muốn biết lý do tại sao lambda không trả về một chuỗi trống khi tôi vượt qua Không là đối số.

Tôi khá mới đối với lambdas nên tôi có thể đã hiểu nhầm một số điều về cách thức hoạt động của chúng.

+2

Bạn đã cam kết một trong những sai lầm ngớ ngẩn cổ điển ... – PaulMcG

Trả lời

17

sử dụng nếu khác xây dựng

f = lambda x:'' if x is None else x 
2

Nó không phải là lambdas là vấn đề ở đây. Đó là thứ pythonic nếu người khác thể hiện bạn đang sử dụng ở đó.

(condition) and (expression1) or (expression2) hầu hết các lần có nghĩa là (condition) ? (expression1) : (expression2) bạn mong đợi, ngoại trừ khi expression1 đánh giá là Sai.

Điều này là do toàn bộ sự việc được đánh giá theo thứ tự. Nếu condition không thành công, expression1 sẽ được đánh giá. Nếu nó là True, nó được trả lại, do đánh giá ngắn mạch, do đó hành vi mong đợi. Nếu không, expression2 sẽ được trả lại. '' đánh giá sai.

+0

Yeah và/hoặc mô hình không phải là rất Pythonic .. không sử dụng nó! Giữ cho nó đơn giản ngu ngốc! –

8

Sự cố trong trường hợp của bạn '' được coi là sai boolean. bool ('') == Sai. Bạn có thể sử dụng

f =lambda x:x if x is not None else '' 
2

Hãy thử short-circuit evaluation:

>>> g = lambda x: x or '' 
>>> g(3) 
3 
>>> g(None) 
'' 
>>> # beware that ... 
>>> g(0) 
'' 
+0

Tôi không nghĩ 'g (0)' trả về những gì OP muốn. –

2

Python cho and một ưu tiên cao hơn or, vì vậy ngoặc rơi ở đây:

lambda x: (x == None and '') or x 

Khi vượt qua None, điều này sẽ trở thành (True and '') or None. Các toán tử boolean của Python làm việc bằng cách trả về một đối số hay cách khác (vì mẹo nhỏ này), do đó, điều này sẽ giảm xuống '' or None và cuối cùng là None.

Bí quyết nhỏ này bắt nguồn từ trước khi Python 2.5, không có số conditional operator. Thông báo trước mà bạn vừa gặp phải là nó không hoạt động như mong đợi khi chi nhánh True có giá trị False. Trừ khi bạn quan tâm đến Python ≤ 2.4, chỉ cần sử dụng toán tử có điều kiện.

4

Vấn đề là Python xử lý chuỗi rỗng là False.Khi bạn vượt qua Không để chức năng của bạn, nó để đánh giá:

None == None and '' or None 

đó (hiệu quả) trở thành:

True and False or None 

thì:

False or None 

và cuối cùng là:

None 

Một giải pháp sẽ là:

lambda x: x if x is not None else '' 

Nếu bạn biết x sẽ hoặc là một chuỗi hoặc None, sau đó bạn có thể tận dụng thực tế là Không cũng là một giá trị False bằng Python:

lambda x: x or '' 
Các vấn đề liên quan