mirror of
https://github.com/github/codeql.git
synced 2026-05-14 19:29:28 +02:00
These tests consist of various Python constructions (hopefully a somewhat comprehensive set) with specific timestamp annotations scattered throughout. When the tests are run using the Python 3 interpreter, these annotations are checked and compared to the "current timestamp" to see that they are in agreement. This is what makes the tests "self-validating". There are a few different kinds of annotations: the basic `t[4]` style (meaning this is executed at timestamp 4), the `t.dead[4]` variant (meaning this _would_ happen at timestamp 4, but it is in a dead branch), and `t.never` (meaning this is never executed at all). In addition to this, there is a query, MissingAnnotations, which checks whether we have applied these annotations maximally. Many expression nodes are not actually annotatable, so there is a sizeable list of excluded nodes for that query.
47 lines
1.4 KiB
Python
47 lines
1.4 KiB
Python
"""Lambda expressions — evaluation order."""
|
|
|
|
from timer import test
|
|
|
|
|
|
@test
|
|
def test_simple_lambda(t):
|
|
"""Lambda creates a function object in one step."""
|
|
f = (lambda x: (x @ t[3] + 1 @ t[4]) @ t[5]) @ t[0]
|
|
result = (f @ t[1])(10 @ t[2]) @ t[6]
|
|
|
|
|
|
@test
|
|
def test_lambda_multiple_args(t):
|
|
"""Lambda call: arguments evaluate left to right."""
|
|
f = (lambda a, b, c: ((a @ t[5] + b @ t[6]) @ t[7] + c @ t[8]) @ t[9]) @ t[0]
|
|
result = (f @ t[1])(1 @ t[2], 2 @ t[3], 3 @ t[4]) @ t[10]
|
|
|
|
|
|
@test
|
|
def test_lambda_default(t):
|
|
"""Default argument evaluated at lambda creation time."""
|
|
val = 5 @ t[0]
|
|
f = (lambda x, y=val @ t[1]: (x @ t[5] + y @ t[6]) @ t[7]) @ t[2]
|
|
result = (f @ t[3])(10 @ t[4]) @ t[8]
|
|
|
|
|
|
@test
|
|
def test_lambda_map(t):
|
|
"""Lambda body runs once per element when consumed by list(map(...))."""
|
|
f = (lambda x: (x @ t[9, 12, 15] * 2 @ t[10, 13, 16]) @ t[11, 14, 17]) @ t[0]
|
|
result = (list @ t[1])((map @ t[2])(f @ t[3], [1 @ t[4], 2 @ t[5], 3 @ t[6]] @ t[7]) @ t[8]) @ t[18]
|
|
|
|
|
|
@test
|
|
def test_immediately_invoked(t):
|
|
"""Arguments evaluated, then immediately-invoked lambda called."""
|
|
result = ((lambda x: (x @ t[2] + 1 @ t[3]) @ t[4]) @ t[0])(10 @ t[1]) @ t[5]
|
|
|
|
|
|
@test
|
|
def test_lambda_closure(t):
|
|
"""Lambda captures enclosing scope; body runs at call time."""
|
|
x = 10 @ t[0]
|
|
f = (lambda: x @ t[3]) @ t[1]
|
|
result = (f @ t[2])() @ t[4]
|