Imposing variable in script
2 views (last 30 days)
I am currently working with a script that uses many functions and sub-functions. The issue is that I have a variable defined at the beginning of the script, but it is changed at some point in one of the functions. I work with maybe 50 or more subfunctions for each of the functions and I can't narrow down where the variable is changed.
Is there a way to impose that the variable at the beginning of the script can not change later, even if it is redifined somewhere ?
I spent many hours trying to see where it changes my variables by making step-by-step and ctrl + F as much as possible, but this is taking too long to cover everything..
Thanks you in advance !
John D'Errico on 23 Apr 2020
Edited: John D'Errico on 23 Apr 2020
First, this sounds as if you are using globals to pass your variables around. UGH. If there is one painful thing that globals will do TO you, it is to create a hell of fiendish proportions for exactly this reason. You cannot then figure out which function has managed to screw up some variable, changing the value in some bad way. Tracking those things down is frustrating and painful. Even worse is if you are using eval in some way to create variable names on the fly - which can consign people to yet another level of Dante's programming hell.
But even if you are passing your variables around in some other, safer way, It can still be a problem to find where you have such a bug.
No. You cannot establish some variable in advance as immutable - something that can never be changed or overridden. Even if you created a function with some name, you can still then later on set a variable to have the same name, dynamically overloading your special function name. So sorry, but no, you cannot enforce a do not touch this variable rule in MATLAB.
That leaves you with debugging where it happens.
I suppose you could try to set a dbstop condition. Since you know the initial value where this variable has been set at, you could use the debugger to set a stop condition if the value of that existing variable is ever not equal to the original value. So among the dbstop options, I see this:
(10) dbstop in FILE if EXPRESSION
So I have a variable with some name: FRED. At the beginning, we have set FRED to some value.
FRED = 17;
Now, at the commandline, you will need to set a debugging stop condition.
dbstop in myfile if ~isequal(FRED,17)
You will need to supply the correct file ename, instead of the one I made up of course. If you have many independent functions in different files, then you would need to set such a stop for each file. If they are all subfunctions or nested functions in the same file, then you should need to do it only once.
Yes, it may take some effort, but it might also be a good programming lesson of how/why not to write code, in case you actually did what I suspect you may have done.
Is there anything else you could do? If the question is just one of finding every line where a certain variable name has been overwritten, then you could use a tool like mgrep. MGREP can be found on the file exchange for free download:
It can search for every line in all of your codes, where a specific string is found. MGREP just treats your m-files as if they are simple text files, then searches through them.
For example, if your variable is named FRED, then you might try something like this command in MATLAB:
mgrep 'FRED =' . casesens on
This will search every m-file in the current working directory, for the exact line where the variable FRED is assigned a new value. (The default, where the case sensitive flag is off would allow it to also find where variables named fred or Fred are changed.) As well, mgrep, by default, will search sub-directories recursively. And you can tell mgrep what top level directory to start the search from. The dot in that command tells mgrep to start the search from the current working directory.
You might want to do that call twice, the second time with no space between the name and the assignment operator.
mgrep 'FRED=' . casesens on
If you then have any line in your code where FRED is overwritten, you could then put a debugging stop on that line.