01/10/2018, 09:50
Về biến trong Python
Em có 1 đoạn code Python như sau:
def do():
def run():
if (i > MAX):
print("Done")
return None
else:
print(i)
i += 1
from time import sleep
sleep(0.1)
run()
MAX = 100
i = 0
run()
do()
Code này em bị lỗi UnboundLocalError: local variable 'i' referenced before assignment
. Dòng i = 0
dù em có khai báo trước hay sau run()
đều bị lỗi như trên. Khi em thêm dòng nonlocal i
vào trước print(i)
thì compile được và có dòng warning SyntaxWarning: name 'i' is used prior to nonlocal declaration
.
Em muốn thắc mắc là, tại sao biến MAX
không cần khai báo global
hay nonlocal
mà biến i phải khai báo nonlocal
(và có thể là global
)?
Bài liên quan
Cách python tìm kiếm biến để xử lý như sau:
Nếu biến chỉ được gọi (reference) thì python sẽ tìm tuần tự từ scope hiện tại đến scope lớn hơn cho đến khi tìm được biến.
Ngược lại nếu biến được gán (assign) thì khi này giá trị biến sẽ bị thay đổi (thực ra chính xác ở đây là ô nhớ mà biến trỏ tới bị thay đổi). Do đó để tránh việc biến ở những scope ngoài bị thay đổi không mong muốn, python sẽ chỉ tìm trong scope hiện tại và trong danh sách những biến được chỉ định global (nonLocal…).
Trong ví dụ của bạn, trong scope của
run()
,MAX
chỉ được reference nhưngi
có khi được assign (i =+ 1
). Khii
được assign, trong scoperun()
chưa tồn tại biếni
nên báo lỗi như trên.Để tránh các lỗi không mong muốn trong python (cũng như các ngôn ngữ khác), tốt nhất nên giới hạn scope của biến càng nhỏ càng tốt bằng cách khai báo biến trong function hiện tại trước khi sử dụng.
Có thể cải thiện ví dụ trên như sau:
mình nghĩ bạn cần khi báo i ngày sau khi dùng lệnh
def
hoặc là khai báo trước khi dùng lệnhif (ì > max):
! bạn thử xem saoThứ nhất, i của mình muốn để ở trong
do()
chứ không phải ở trongrun()
, vì mình còn dùng i ở ngoàirun()
mà ở trongdo()
nữa; nên mình không thể khai báo i trong trướcif
được.Thứ 2, bạn khuyên mình khai báo i ngay sau khi dùng def, vậy bạn đã thử chạy code chưa?
Ideone.com
Ideone is something more than a pastebin; it's an online compiler and debugging tool which allows to compile and run code online in more than 40 programming languages.
Hãy là người comment có trách nhiệm. Không phải cứ comment bừa là được đâu.