{"id":2325,"date":"2025-09-23T13:28:58","date_gmt":"2025-09-23T13:28:58","guid":{"rendered":"https:\/\/www.cmarix.com\/qanda\/?p=2325"},"modified":"2026-02-05T11:59:08","modified_gmt":"2026-02-05T11:59:08","slug":"unboundlocalerror-in-python-what-it-means","status":"publish","type":"post","link":"https:\/\/www.cmarix.com\/qanda\/unboundlocalerror-in-python-what-it-means\/","title":{"rendered":"Why does Python throw a UnboundLocalError even When a Variable seems Defined Globally?"},"content":{"rendered":"\n<p>If you assign a value to a variable anywhere inside a function, Python assumes that variable is local to that function. So even if there\u2019s a global variable with the same name, Python won\u2019t look at it. It treats your variable as a separate, uninitialized local one. That\u2019s why you get the error when you try to use it before assigning a value.<\/p>\n\n\n\n<p><strong>Want to fix it? You\u2019ve got two options:<\/strong><\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>If you really want to use the global variable, add global variable_name inside the function.<\/li>\n\n\n\n<li>Or better yet, avoid this pattern. It\u2019s often cleaner to pass variables into functions and return new values.<\/li>\n<\/ul>\n\n\n\n<h2 class=\"wp-block-heading\">Description of the Problem<\/h2>\n\n\n\n<p><strong>You&#8217;re using a global variable inside a function, but Python throws this error:<\/strong><\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>counter = 10\n\ndef increment():\n    counter += 1\n    print(counter)\n\nincrement()<\/code><\/pre>\n\n\n\n<p><strong>Output:<\/strong><\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>UnboundLocalError: local variable 'counter' referenced before assignment<\/code><\/pre>\n\n\n\n<p>You&#8217;re confused \u2014 counter is clearly defined at the top level. Why is Python treating it like it\u2019s undefined inside the function?<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Why This Happens<\/h2>\n\n\n\n<p>This error occurs when you try to modify a global variable without declaring it as global inside a function. In Python, when you assign a value to a variable anywhere inside a function, Python treats it as a local variable unless explicitly told otherwise.<\/p>\n\n\n\n<p><strong>So in this line:<\/strong><\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>counter += 1<\/code><\/pre>\n\n\n\n<p>Python treats counter as a new local variable. But since it hasn&#8217;t been assigned before that line, it throws an UnboundLocalError.<\/p>\n\n\n\n<p>Even though counter exists globally, Python doesn&#8217;t look at that definition because it assumes you&#8217;re trying to create a new local variable.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">How to Resolve the UnboundLocalError in 3 Simple Steps<\/h2>\n\n\n\n<h3 class=\"wp-block-heading\">Step 1: Use the global keyword if you want to modify the global variable<\/h3>\n\n\n\n<p>To tell Python that you&#8217;re referring to the global counter, use the global keyword:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>counter = 10\n\ndef increment():\n    global counter\n    counter += 1\n    print(counter)\n\nincrement()  # Output: 11<\/code><\/pre>\n\n\n\n<p>Now Python knows you&#8217;re not creating a new local variable \u2014 you&#8217;re modifying the global one.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">Step 2: Avoid global when possible &#8211; prefer return values<\/h3>\n\n\n\n<p>Using global can make code harder to debug and maintain. Instead, consider returning values and reassigning them:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>def increment(counter):\n    counter += 1\n    return counter\n\ncounter = 10\ncounter = increment(counter)\nprint(counter)  # Output: 11<\/code><\/pre>\n\n\n\n<p>This makes data flow clear and avoids side effects.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">Step 3: Use nonlocal for modifying variables in nested functions<\/h3>\n\n\n\n<p>If you&#8217;re working with <strong>nested functions<\/strong> and want to modify a variable from the enclosing scope (but not global), use nonlocal:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>def outer():\n    counter = 0\n\n    def inner():\n        nonlocal counter\n        counter += 1\n        print(counter)\n\n    inner()\n    inner()\n\nouter()<\/code><\/pre>\n\n\n\n<p>This modifies counter in the outer() function, not the global scope.<\/p>\n\n\n\n<p><strong>Best Practices:<\/strong><\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>Use the global keyword if you <em>must<\/em> modify a global variable<\/li>\n\n\n\n<li>Prefer passing and returning variables to avoid using global<\/li>\n\n\n\n<li>Use nonlocal for modifying variables in nested scopes (closures)<\/li>\n<\/ul>\n\n\n\n<p>Understanding Python\u2019s scoping rules\u2014Local, Enclosing, Global, and Built-in (LEGB)\u2014is key to avoiding bugs like UnboundLocalError.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Conclusion<\/h2>\n\n\n\n<p>Understanding Python&#8217;s scoping rules can save you from frustrating bugs like UnboundLocalError. If you&#8217;re building complex Python applications and want to get things right from the start, it might be time to <a href=\"https:\/\/www.cmarix.com\/hire-python-developers.html\">hire Python developers<\/a> who understand these subtleties. A slight change in scope can create big problems if you&#8217;re not careful.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>If you assign a value to a variable anywhere inside a function, Python assumes that variable is local to that function. So even if there\u2019s a global variable with the same name, Python won\u2019t look at it. It treats your variable as a separate, uninitialized local one. That\u2019s why you get the error when you [&hellip;]<\/p>\n","protected":false},"author":2,"featured_media":2327,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[163,3],"tags":[],"class_list":["post-2325","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-python","category-web"],"acf":[],"_links":{"self":[{"href":"https:\/\/www.cmarix.com\/qanda\/wp-json\/wp\/v2\/posts\/2325","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.cmarix.com\/qanda\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.cmarix.com\/qanda\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.cmarix.com\/qanda\/wp-json\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"https:\/\/www.cmarix.com\/qanda\/wp-json\/wp\/v2\/comments?post=2325"}],"version-history":[{"count":2,"href":"https:\/\/www.cmarix.com\/qanda\/wp-json\/wp\/v2\/posts\/2325\/revisions"}],"predecessor-version":[{"id":2329,"href":"https:\/\/www.cmarix.com\/qanda\/wp-json\/wp\/v2\/posts\/2325\/revisions\/2329"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/www.cmarix.com\/qanda\/wp-json\/wp\/v2\/media\/2327"}],"wp:attachment":[{"href":"https:\/\/www.cmarix.com\/qanda\/wp-json\/wp\/v2\/media?parent=2325"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.cmarix.com\/qanda\/wp-json\/wp\/v2\/categories?post=2325"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.cmarix.com\/qanda\/wp-json\/wp\/v2\/tags?post=2325"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}