Но если в кратце. Есть 3 скоупа(контекста). Local, global и built-in.
Когда ты внутри функции объявляешь переменную она храниться внутри local конкретно этой функции, то есть из вне функции ты к переменной не имеешь доступа.
Когда переменная объявлена в корне модуля (то что ты объявил "а"). Она сохраняется в global (глобально для модуля). К нему доступ имеют все функции и классы этого модуля.
Builtins - встроенные объекты питона (переменные которые не нужно импортировать по дефолту, str, list, print, и тд). По сути все что ты используешь без импорта. Можно найти в модуле builtins (import builtins).
Так вот. Когда ты обращаешься к переменной, питон ищет её в этих 3-х скоупах. В порядке local, global, built-in.
В твоем случаи твой локальный "а" - название первого аргумента функции, перекрыл глобальный "а" - который ты объявил в начале скрипта. И чтобы дать понять питону что ты хочешь обратиться к глобальному "а", а не локальному, ты добавляешь global.