如何避免编写request.GET.get()两次才能打印?

我来自PHP背景,想知道是否有办法在Python中做到这一点。

在PHP中,你可以像这样一石二鸟:

代替:

if(getData()){ $data = getData(); echo $data; } 

我可以做这个:

 if($data = getData()){ echo $data; } 

您检查getData()存在,如果存在,则将其分配给一个语句中的variables。

我想知道是否有办法在Python中做到这一点? 所以不要这样做:

 if request.GET.get('q'): q = request.GET.get('q') print q 

避免编写request.GET.get('q')两次。

可能不完全是你在想什么,但…

 q = request.GET.get('q') if q: print q 

这个?

看到我8岁的食谱在这里只是这个任务。

 # In Python, you can't code "if x=foo():" -- assignment is a statement, thus # you can't fit it into an expression, as needed for conditions of if and # while statements, &c. No problem, if you just structure your code around # this. But sometimes you're transliterating C, or Perl, or ..., and you'd # like your transliteration to be structurally close to the original. # # No problem, again! One tiny, simple utility class makes it easy...: class DataHolder: def __init__(self, value=None): self.value = value def set(self, value): self.value = value; return value def get(self): return self.value # optional but handy, if you use this a lot, either or both of: setattr(__builtins__,'DataHolder',DataHolder) setattr(__builtins__,'data',DataHolder()) # and now, assign-and-set to your heart's content: rather than Pythonic while 1: line = file.readline() if not line: break process(line) # or better in modern Python, but quite far from C-like idioms: for line in file.xreadlines(): process(line) # you CAN have your C-like code-structure intact in transliteration: while data.set(file.readline()): process(data.get()) 

亚历克斯的答案的变化:

 class DataHolder: def __init__(self, value=None, attr_name='value'): self._attr_name = attr_name self.set(value) def __call__(self, value): return self.set(value) def set(self, value): setattr(self, self._attr_name, value) return value def get(self): return getattr(self, self._attr_name) save_data = DataHolder() 

用法:

 if save_data(get_input()): print save_data.value 

或者如果您更喜欢另一个界面:

 if save_data.set(get_input()): print save_data.get() 

我会发现这有助于在if-elif-elif-elif等结构中testing一系列正则expression式,就像在这个SO问题中一样 :

 import re input = u'test bar 123' save_match = DataHolder(attr_name='match') if save_match(re.search('foo (\d+)', input)): print "Foo" print save_match.match.group(1) elif save_match(re.search('bar (\d+)', input)): print "Bar" print save_match.match.group(1) elif save_match(re.search('baz (\d+)', input)): print "Baz" print save_match.match.group(1) 
 q = request.GET.get('q') if q: print q else: # q is None ... 

没有办法一次做任务和条件。

如果get()在不存在的时候抛出一个exception,你可以这样做

 try: q = request.GET.get('q') print q except : pass 

那么,这将是一个方法

 q = request.GET.get('q') if q: print q 

一个简短的(但不是优越的,由于打印没什么)的方式将是

 print request.GET.get('q') or '', 
 config_hash = {} tmp_dir = ([config_hash[x] for x in ["tmp_dir"] if config_hash.has_key(x)] or ["tmp"])[0] print tmp_dir config_hash["tmp_dir"] = "cat" tmp_dir = ([config_hash[x] for x in ["tmp_dir"] if config_hash.has_key(x)] or ["tmp"])[0] print tmp_dir 

一个可能的方法来做到这一点,而不必在之前设置variables,可能是这样的:

 if (lambda x: globals().update({'q':x}) or True if x else False)(request.GET.get('q')): print q 

..这只是为了好玩 – 这种方法不应该被使用,因为它很丑陋,一见难以理解,它会创build/覆盖一个全局variables(只有当条件满足时,虽然)

只需尝试:

 print(request.GET.get('q', '')) 

如果第一个参数不存在,基本上不会显示任何内容(请参阅dict.get )。


另一种解决scheme是在Python中使用条件expression式:

 <expression1> if <condition> else <expression2> 

但是最终会重复两次variables,例如:

 print(request.GET.get('q') if request.GET.get('q') else '') 

对于循环中的variables赋值,请在此处检查。