Short-circuit evaluation like Python's "and" while storing results of checks
<p>I have multiple expensive functions that return results.  I want to return a tuple of the results of all the checks if all the checks succeed.  However, if one check fails I don't want to call the later checks, like the short-circuiting behavior of <code>and</code>.  I could nest <code>if</code> statements, but that will get out of hand if there are a lot of checks.  How can I get the short-circuit behavior of <code>and</code> while also storing the results for later use?</p>

<pre><code>def check_a():
    # do something and return the result,
    # for simplicity, just make it "A"
    return "A"

def check_b():
    # do something and return the result,
    # for simplicity, just make it "B"
    return "B"

...
</code></pre>

<p>This doesn't short-circuit:</p>

<pre><code>a = check_a()
b = check_b()
c = check_c()

if a and b and c:
    return a, b, c
</code></pre>

<p>This is messy if there are many checks:</p>

<pre><code>if a:
   b = check_b()

   if b:
      c = check_c()

      if c:
          return a, b, c
</code></pre>

<p>Is there a shorter way to do this?</p>

<p>In other languages that did have <a href="http://stackoverflow.com/q/4869770/1048572">assignments as expressions</a> you would be able to use</p>

<pre><code>if (a = check_a()) and (b = check_b()) and (c = check_c()):
</code></pre>

<p>but Python is no such language. Still, we can circumvent the restriction and emulate that behaviour:</p>

<pre><code>result = []
def put(value):
    result.append(value)
    return value

if put(check_a()) and put(check_b()) and put(check_c()):
    # if you need them as variables, you could do
    # (a, b, c) = result
    # but you just want
    return tuple(result)
</code></pre>

<p>This might loosen the connection between the variables and function calls a bit too much, so if you want to do lots of separate things with the variables, instead of using the <code>result</code> elements in the order they were put in the list, I would rather avoid this approach. Still, it might be quicker and shorter than some loop.</p>

python short-circuiting