python - Is it "bad" to define closures at the top level, only to be called inside a function? If so: alternatives? -
I'm tagging this as a "language-agnostic" because I'm asking that a general theory, but I am using R and Python as my examples.
I have written an R script on the basis of this MWE:
# # does not work: Plus_I < - Function (X) X + I Times Ii & lt; - Function (x) x * i loop_i & lt; - Function (x) {for (i in 1: 2) {x & lt; - plus_i (x) x & lt; - times_i (x)} x} loop_i (3)
but it failed in error by plus_i (x): object 'I' did not get '/'> RK lexical Due to scoping I could not stop my way around from eval
.
The Python equivalent also fails:
## does not work: def Plus_i (x): return x + i def times_i (x): return x * i Def loop_i (x): # Be careful in [1, 2] for # mutual objects i: x = plus_i (x) x = times_i (x) return x loop_i (3)
In my understanding, these programs will work in a dynamically scopid language, but R and Python are both static / interpretive scods. If this is the case, then is there any type of anti-paradigm or otherwise writing "bad" R and Python code like this? Is it just "obviously obvious", or does it come from the depth?
Edit: It seems, in fact, it goes deeper. obviously . The question still applies.
Note that the program is not used outside of plus_i
and times_i
in loop_i
. But I do not want to not define plus_i
and times_i
inside loop_i
because I think it Seriously the readability of the code hurts (which is not so easy in this example). Whatever I do not want to do, it makes i
a clear function argument, because there are many such i
and then this code is less readable and seems to debug and More difficult (to keep track of locally defined and that has been passed)
Another option would be to create a new environment, define plus_i
and times_i
inside it, and then pass it on loop_i
Please. But it still feels like using an off-label environment. Edit: Or, Environment (plus_i) & lt; - Reset the environment ()
if you read , You will understand that there are four environments to keep in mind for each function:
- Defined environment - where the code of the function is stored
- Calling environment - the function Which environment was called from.
- Parental environments - where the function looks for symbols if it is closed.
- Local Area - The Edok Interface Every time you implement the function, whose parent is the environment described above.
In this case, you are outside of the plus_i
and Times_I
loop, hence their original environment will be the global environment - this is where They search for additional symbols (like i
), and they will not get the function to push with nudge, where you can force them by telling them.
plus_i & lt; - Function (x) x + i times_i & lt; - function (x) x * i Loop_i & lt; - Function (x) {Environment (plus_i) & lt; - Environmental () # See "here" in the local scope environment (times_i), & lt; - environment () #for loop_i, i! (1: 2) in (i in 1: 2) {x
is implied. In general, however,loop_i I
is a bad idea in the form of an argument: if you provide a task that refers to the "incomplete" symbol, which it has to do with its logic list or default native environment If you can not get it in, then imagine it would be very difficult for others to use that if there are several dozen lines of code in the code with hiding in any place ofi
; How would anyone know if the function depends oni
? It may be fine for small scripts but this will not be good development hygiene for a long time.
Comments
Post a Comment