Measuring Function Execution Time Using Python Decorators
Decorators provide a clean way to wrap additoinal behavior around fnuctions. The following implementation defines a measure_runtime decorator that records how long a function takes to execute, then prints the result.
import time
import os
import requests
from html import unescape
def measure_runtime(func):
def wrapper(*args, **kwargs):
start = time.perf_counter()
result = func(*args, **kwargs)
elapsed = time.perf_counter() - start
print(f"[Timing] {func.__name__} took {elapsed:.4f} seconds")
return result
return wrapper
class PageFetcher:
def __init__(self):
self.target_url = ''
@measure_runtime
def fetch_page(self, url):
headers = {'User-Agent': 'Mozilla/5.0 (compatible; ExampleBot/1.0)'}
try:
response = requests.get(url, headers=headers, timeout=10)
response.raise_for_status()
content = unescape(response.text)
return content
except requests.exceptions.RequestException as e:
print(f"Request failed: {e}")
return None
@measure_runtime
def run(self):
self.target_url = 'http://www.example.com'
self.fetch_page(self.target_url)
print('Finished fetching.')
@measure_runtime
def list_files_recursive(root_path):
for entry in os.listdir(root_path):
full = os.path.join(root_path, entry)
if os.path.isdir(full):
list_files_recursive(full)
else:
print(full)
if __name__ == '__main__':
fetcher = PageFetcher()
fetcher.run()
cwd = os.path.abspath('.')
list_files_recursive(cwd)
In this implementation, the decorator uses time.perf_counter() for high‑resolution timing. It wraps the original function, captures the moment before and after the call, and logs the duration along with the function's name. This pattern works uniformly whether the decorated target is a standalone function, a method inside a class, or even a recursive call like the directory listing example.