Which languages, require the programmer to EXPLICITLY manage "environments"?

1 jerng 2 5/26/2025, 6:34:52 PM
QUESTION : can you point me to any existing languages where it is common / mandatory to pass around a list/object of data bound to variables which are associated with scopes? (Thank you.)

MOTIVATION : I recently noticed that "environment objects / envObs" (bags of variables in scope, if you will) and the stack of envObs, are hidden from programmers in most languages, and handled IMPLICITLY.

1. For example, in JavaScript, you can say (var global.x) however it is not mandatory, and there is sugar such you can say instead (var x). This seems to be true in C, shell command language, Lisp, and friends.

2. Languages which have a construct similar to, (let a=va, b=vb, startscope dosoemthing endscope), such as Lisp, do let you explicitly pass around envObs, but this isn't mandatory for the top-level global scope to begin with.

3. In many cases, the famous "stack overflow" problem is just a pile-up of too many envObjs, because "the stack" is made of envObs.

4. Exception handling (e.g. C's setjump, JS's try{}catch{}) use constructs such as envObjs to reset control flow after an exception is caught.

5. Generally, I was surprised to find that this pattern of hiding the global envObs and handling the envObjs IMPLICITLY is so pervasive. It seems that this obfuscates the nature of programming computers from programmers, leading to all sorts of confusions about scope for new learners. Moreover it seems that exposing explicit envObs management would allow/force programmers to write code that could be optimised more easily by compilers. So I am thinking to experiment with this in future exercises.

Comments (2)

sargstuff · 1d ago
Historically, the lower the level of coding, the more the programming is expected to manage the environment(s). But somewhat dependent upon standards & how programming language abstractions/constructs permit interaction with different logic planes/levels. aka OS, user gui, user shell, hardware, etc.

Lisp and C focus on different logic planes (historically, os/hw for C vs. os/user for Lisp) & different categorical approaches to programming (linear vs. non-linear).

Human doing envObs management on own doesn't make for 'standard' approaches needed by a compiler to do optimizations.

Check out turing machine[1] for the 'extreme' example of 'endless memory' & what binary file formats 'hide' from the user.

----------------------------------------

Messing around with typical unix shell (ksh, sh), one can impliment the equivalent of what C & Lisp language level provide natively, but gets really unwieldy fast relative to using Lisp/C).

Traditional unix shells pass around "flattened" list/object data bound to variable(s) where scope is defined by how script was envoked. aka discard variable changes on exit or overwrite values of existing values.[0]

For shell script concurrency, one can dump to file, call script, load data from file, and overwrite file with new values before returning to 'caller' in order to make sure things aren't over written by multiple envoked shell scripts. Within shell script file, when calling a function, need to define scope. Not defining scope when 'program' get's large (~5000) lines of code, makes figuring out where in program value is being used/changed, difficult.

----------------------------------------------------

[0] : https://www.baeldung.com/linux/sourcing-vs-executing-shell-s...

[1] : https://www.geeksforgeeks.org/turing-machine-in-toc/

jerng · 1d ago
Thanks, it is an insightful consideration of the subject.