title: Is "x < y < z" faster than "x < y and y < z"?
body: <p>From <a href="https://wiki.python.org/moin/PythonSpeed#Take_advantage_of_interpreter_optimizations" rel="nofollow noreferrer">this page</a>, we know that:</p>
  
  <blockquote>
    <p>Chained comparisons are faster than using the <code>and</code> operator.
    Write <code>x &lt; y &lt; z</code> instead of <code>x &lt; y and y &lt; z</code>.</p>
  </blockquote>
  
  <p>However, I got a different result testing the following code snippets:</p>
  
  <pre><code>$ python -m timeit "x = 1.2" "y = 1.3" "z = 1.8" "x &lt; y &lt; z"
  1000000 loops, best of 3: 0.322 usec per loop
  $ python -m timeit "x = 1.2" "y = 1.3" "z = 1.8" "x &lt; y and y &lt; z"
  1000000 loops, best of 3: 0.22 usec per loop
  $ python -m timeit "x = 1.2" "y = 1.3" "z = 1.1" "x &lt; y &lt; z"
  1000000 loops, best of 3: 0.279 usec per loop
  $ python -m timeit "x = 1.2" "y = 1.3" "z = 1.1" "x &lt; y and y &lt; z"
  1000000 loops, best of 3: 0.215 usec per loop
  </code></pre>
  
  <p>It seems that <code>x &lt; y and y &lt; z</code> is faster than <code>x &lt; y &lt; z</code>. <strong>Why?</strong></p>
  
  <p>After searching some posts in this site (like <a href="https://stackoverflow.com/questions/1664292/what-does-evaluated-only-once-mean-for-chained-comparisons-in-python">this one</a>) I know that "evaluated only once" is the key for <code>x &lt; y &lt; z</code>, however I'm still confused. To do further study, I disassembled these two functions using <code>dis.dis</code>:</p>
  
  <pre><code>import dis
  
  def chained_compare():
          x = 1.2
          y = 1.3
          z = 1.1
          x &lt; y &lt; z
  
  def and_compare():
          x = 1.2
          y = 1.3
          z = 1.1
          x &lt; y and y &lt; z
  
  dis.dis(chained_compare)
  dis.dis(and_compare)
  </code></pre>
  
  <p>And the output is:</p>
  
  <pre><code>## chained_compare ##
  
    4           0 LOAD_CONST               1 (1.2)
                3 STORE_FAST               0 (x)
  
    5           6 LOAD_CONST               2 (1.3)
                9 STORE_FAST               1 (y)
  
    6          12 LOAD_CONST               3 (1.1)
               15 STORE_FAST               2 (z)
  
    7          18 LOAD_FAST                0 (x)
               21 LOAD_FAST                1 (y)
               24 DUP_TOP
               25 ROT_THREE
               26 COMPARE_OP               0 (&lt;)
               29 JUMP_IF_FALSE_OR_POP    41
               32 LOAD_FAST                2 (z)
               35 COMPARE_OP               0 (&lt;)
               38 JUMP_FORWARD             2 (to 43)
          &gt;&gt;   41 ROT_TWO
               42 POP_TOP
          &gt;&gt;   43 POP_TOP
               44 LOAD_CONST               0 (None)
               47 RETURN_VALUE
  
  ## and_compare ##
  
   10           0 LOAD_CONST               1 (1.2)
                3 STORE_FAST               0 (x)
  
   11           6 LOAD_CONST               2 (1.3)
                9 STORE_FAST               1 (y)
  
   12          12 LOAD_CONST               3 (1.1)
               15 STORE_FAST               2 (z)
  
   13          18 LOAD_FAST                0 (x)
               21 LOAD_FAST                1 (y)
               24 COMPARE_OP               0 (&lt;)
               27 JUMP_IF_FALSE_OR_POP    39
               30 LOAD_FAST                1 (y)
               33 LOAD_FAST                2 (z)
               36 COMPARE_OP               0 (&lt;)
          &gt;&gt;   39 POP_TOP
               40 LOAD_CONST               0 (None)
  </code></pre>
  
  <p>It seems that the <code>x &lt; y and y &lt; z</code> has less dissembled commands than <code>x &lt; y &lt; z</code>. Should I consider <code>x &lt; y and y &lt; z</code> faster than <code>x &lt; y &lt; z</code>?</p>
  
  <p>Tested with Python 2.7.6 on an Intel(R) Xeon(R) CPU E5640 @ 2.67GHz.</p>