How do you check if a function has been executed python?

A minimal example using unittest.mock.Mock from the standard library:

from unittest.mock import Mock

def example[]:
    pass

example_mock = Mock[side_effect=example]
example_mock[]
#Pseudocode:
if example_mock.called:
   print["foo bar"]

Console output after running the script:

foo bar

This approach is nice because it doesn't require you to modify the example function itself, which is useful if you want to perform this check in some unit-testing code, without modifying the source code itself [EG to store a has_been_called attribute, or wrap the function in a decorator].

Explanation

As described in the documentation for the unittest.mock.Mock class, the side_effect argument to the Mock[] constructor specifies "a function to be called whenever the Mock is called".

The Mock.called attribute specifies "a boolean representing whether or not the mock object has been called".

The Mock class has other attributes you may find useful, EG:

call_count: An integer telling you how many times the mock object has been called

call_args: This is either None [if the mock hasn’t been called], or the arguments that the mock was last called with

call_args_list: This is a list of all the calls made to the mock object in sequence [so the length of the list is the number of times it has been called]. Before any calls have been made it is an empty list

The Mock class also has convenient methods for making assert statements based on how many times a Mock object was called, and what arguments it was called with, EG:

assert_called_once_with[*args, **kwargs]: Assert that the mock was called exactly once and that that call was with the specified arguments

Last year I ran into a situation where I needed to know if a function had been called. Basically we were trying to prevent shutting down a Twisted event loop twice or starting two of them. Anyway, in my research I stumbled across a fun post on StackOverflow that showed a couple of ways to do this.

The first made use of the fact that everything in Python is an object, including the function itself. Let's take a look at a simple example:

def self_aware_function[a, b]:
    self_aware_function.has_been_called = True
    return a + b

if __name__ == '__main__':
    self_aware_function.has_been_called = False

    for i in range[2]:
        if self_aware_function.has_been_called:
            print['function already called']
        else:
            print['function not called']

        self_aware_function[1, 2]

In this example, we create an attribute on the function that we named has_been_called. We set it to True when the function is called. When you start your program, you will want to initialize that attribute to False, which we do above. Then we use a for loop to loop twice. The first time through it will check if the function has been called. Since it hasn't, you will see it fall to the else statement. Now that we called the function, the second time through the loop the first part of the if statement executes.

That StackOverflow post also mentions a neat way to use a decorator to track function calls. Here's an example I wrote:

import functools


def calltracker[func]:
    @functools.wraps[func]
    def wrapper[*args]:
        wrapper.has_been_called = True
        return func[*args]
    wrapper.has_been_called = False
    return wrapper

@calltracker
def doubler[number]:
    return number * 2

if __name__ == '__main__':
    if not doubler.has_been_called:
        print["You haven't called this function yet"]
        doubler[2]

    if doubler.has_been_called:
        print['doubler has been called!']

In this example, I import functools and create a decorator that I dubbed calltracker. In this function, we set up the same attribute that we did in the previous example, but in this case we attach it to our wrapper [i.e. the decorator]. Then we decorate a function and give our code a try. The first if statement checks to see if the function has been called yet. It hasn't, so we go ahead and call it. Then we confirm that the function was called in our second if statement.

Wrapping Up

While this stuff is certainly useful at runtime, you can also do similar things using Python's trace module to trace through the execution of your code. This sort of thing is also done via coverage tools. You will also find this kind of functionality in Python Mock objects as a Mock can tell when it has been called.

Anyway, you will hopefully find this exercise as interesting as I did. While I already knew that everything in Python was an object, I hadn't thought about using that functionality to add attributes to functions.

How do you check if a function has been executed?

One way to check if a function is defined is to test it with an if statement. The trick is to test the function as a method of the window object. The code in the brackets will execute if the function is defined.

How are functions executed in Python?

Use the keyword def to declare the function and follow this up with the function name. Add parameters to the function: they should be within the parentheses of the function. End your line with a colon. Add statements that the functions should execute.

What is def check in Python?

Python def keyword is used to define a function, it is placed before a function name that is provided by the user to create a user-defined function. In python, a function is a logical unit of code containing a sequence of statements indented under a name given using the “def” keyword.

Is the function executed before it is called?

The statements inside the function do not get executed until the function is called, and the function definition generates no output.

When a function is called in Python?

A function is a block of code which only runs when it is called. You can pass data, known as parameters, into a function. A function can return data as a result.

How does Python know if a function is a generator?

Create Generators in Python If a function contains at least one yield statement [it may contain other yield or return statements], it becomes a generator function. Both yield and return will return some value from a function.

Chủ Đề