Не понимаю область видимости с словарями
Есть такая функция в коде:
def on_group(_, callback_query):
msg = callback_query.message
print(group_names)
group_id.clear()
with open(groups_path, "r") as my_file:
group_names = json.load(my_file)
for i in group_names:
group_id.append(group_names[i])
Group_names и group_id объявлены как словарь и список в начале кода. В строке 3 выдаёт ошибку:
Traceback (most recent call last):
File "C:\Users\kolch\AppData\Local\Programs\Python\Python310\lib\site-packages\pyrogram\dispatcher.py", line 242, in handler_worker
await self.loop.run_in_executor(
File "C:\Users\kolch\AppData\Local\Programs\Python\Python310\lib\concurrent\futures\thread.py", line 58, in run
result = self.fn(*self.args, **self.kwargs)
File "c:\Users\kolch\Desktop\all\Prog\py\Group_filter\filter_main.py", line 132, in on_group
print(group_names)
UnboundLocalError: local variable 'group_names' referenced before assignment
Проблема с видимостью переменных или что?
Ответы (1 шт):
вот так работать будет, но не является хорошей практикой
group_names = {}
def on_group():
print(group_names)
on_group()
То же самое, но верное использование
def on_group(param):
print(param)
group_names = {}
on_group(group_names)
Основной принцип: функция не должна работать с переменными вне зоны ее видимости и глобальными переменными. Все необходимые данные функция получает на вход, все что было изменено возвращается из функции через return
А вот так работать не будет
def on_group():
print(group_names)
on_group()
UPD START
И вот так работать не будет
def on_group():
print(group_names)
group_names = {1:"name"}
group_names = {}
on_group()
Во втором случае, если вы используете оператор присваивания, создается переменная внутри области видимости фунции. При загрузке вашей функции интерпретатор решает, что глобальная область видимости для group_names не должна использоваться внтури локальной области видимости функции, что и приводит к ошибке, когда вы пытаетесь сослаться на переменную до того, как она будет назначена локально.
Если же, вы не будете присваивать (полностью перезаписывать словарь), а просто будете его менять, добавляя или изменяя его, то все будет работать
def on_group():
print(group_names)
group_names[1] = "name"
group_names = {}
on_group()
UPD END
может вот так будет понятна моя мысль, про не использование переменных вне области видимости функции
def on_group(_, callback_query):
msg = callback_query.message
group_id.clear()
with open(groups_path, "r") as my_file:
group_names = json.load(my_file)
for i in group_names:
group_id.append(group_names[i])
return group_names
group_names = {}
group_names = on_group(_, query)