π Introduction
In programming, scope defines the part of the program where a variable can be accessed. Different programming languages follow different scoping rules, which determine how variables are resolved inside functions. The two most common scoping models are lexical (static) scope and dynamic scope. Knowing the difference is important because it changes how functions behave when they try to use variables.
π What is Lexical Scope?
Lexical scope, also called static scope, means that the scope of a variable is decided by where the function is written in the code. It does not matter where the function is called from; what matters is its position in the source code. Most modern programming languages, including JavaScript, Python, and C, use lexical scoping.
Example
function outer() {
let name = "Alice";
function inner() {
console.log(name); // β
Can access 'Alice' because inner is inside outer
}
inner();
}
outer();
Here, the function inner
can access the variable name
from outer
because it is written inside outer
. This is a direct result of lexical scoping.
π What is Dynamic Scope?
Dynamic scope means that the scope of a variable is decided by where the function is called from, not where it is written. In this model, the program looks at the runtime call stack to decide which variable to use. This makes variable resolution depend on the execution flow rather than the code structure.
JavaScript does not use dynamic scope, but some older languages (like early Lisp) supported it.
Pseudo Example (Dynamic Scope Behavior)
let name = "Global";
function inner() {
console.log(name); // What will this print?
}
function outer() {
let name = "Alice";
inner();
}
outer();
In lexical scope (JavaScriptβs real behavior) β It prints Global
, because inner
was written outside of outer
.
In dynamic scope (if JavaScript had it) β It would print Alice
, because inner
was called inside outer
.
βοΈ Key Differences Between Lexical and Dynamic Scope
1. How Scope is Decided
2. Common Usage in Languages
Lexical Scope: Used in most modern programming languages like JavaScript, C, C++, Python, and Java.
Dynamic Scope: Rare today, but seen in older languages and special cases.
3. Predictability
Lexical Scope: Easier to understand and debug because you know by looking at the code where variables come from.
Dynamic Scope: Harder to understand, since the meaning of a variable changes depending on the execution flow.
4. Closures
Lexical Scope: Supports closures. Functions can remember variables from the environment where they were created.
Dynamic Scope: Closures are not possible in the same way because variable lookup depends on the calling environment.
π§βπ» Closures in Lexical Scope
Closures are one of the most powerful features of lexical scope. A closure happens when a function keeps access to variables from its parent scope, even after the parent function has finished running.
Example
function outer() {
let counter = 0;
function increment() {
counter++;
return counter;
}
return increment;
}
const add = outer();
console.log(add()); // 1
console.log(add()); // 2
Here, the function increment
remembers the variable counter
from the outer
function, even though outer
has finished executing. This works because of lexical scope.
β
Summary
Lexical scope and dynamic scope are two ways to decide how variables are accessed in a program. In lexical scope, variable access is based on where the function is written in the code, while in dynamic scope, it depends on where the function is called. JavaScript and most modern languages use lexical scope because it is easier to predict, easier to debug, and it enables powerful features like closures. Dynamic scoping is less common today and is mostly studied for academic or historical purposes.