Hello together,
I'm writing many function which i often use during a matlab session. To make them a little more compfortalbe to use i'd like to use a data structure in some way, where i can store some preference data. The preference data is for example some input arguments the functions have in common. But because the values of these input arguments change from time to time, so i can not set it as default values in the function.
Global variables look perfect for this task, but i've read a lot of comments that global variables are bad and i'd rather avoid using them. But what other ways are there, to store my preference data and use it in different functions.
thank you for your help.
Rafael

댓글 수: 1

Jan
Jan 2017년 11월 29일
This is a good question, +1. You state "Global variables look perfect for this task". The magic core in this formulation is "look": In fact, globals look like they solve the problems and they really do so - but in a long term view they will cause even more troubles, which can grow to a such severe level, that the code cannot be debugged or maintained anymore.

댓글을 달려면 로그인하십시오.

 채택된 답변

Jan
Jan 2017년 11월 29일

2 개 추천

You can create a "global function" to store static parameters:
function G = theGlobalData()
G.pi = 3.14;
G.imag = 1i;
G.PIN = 5553;
end
You might add some input arguments also or store G persistently:
function G = theGlobalData(Name, Value)
persistent G_
if isempty(G_)
G_.pi = 3.14;
G_.imag = 1i;
G_.PIN = 5553;
end
if nargin > 0
G_.(Name) = Value;
end
G = G_;
end
This shares the problem of global variables, that e.g. running multiple instances of your program can cause collisions of the values. But at least you can debug each access of this function. Setting a breakpoint in it allows to track all events.
I'd prefer sharing the struct inside the code by using input and output arguments. Passing an additional argument is neither clumsy nor slow and there is no danger of interferences with other instances of your code or other software.
These ideas are "create a parameters function" and "pass a struct" of Stephen's answer.

댓글 수: 7

Thanks alot Jan for this answer.
Would you recomend to load a .mat file containing the start values istead of
if isempty(G_)
G_.pi = 3.14;
G_.imag = 1i;
G_.PIN = 5553;
end
and then saving the .mat when matlab closes?
I'd like to reuse the current set of G_ on a new matlab session. Or ist this prone to error?
Jan
Jan 2017년 11월 29일
편집: Jan 2017년 11월 29일
@Rafael: Storing the struct for the next Matlab session is fine, e.g.:
function G = YourGlobalFcn(Name, Value)
persistent G_
if isempty(G_)
% Check if Matlab know the preferences already:
if ispref('Rafael', 'G_')
fprintf('::: Loading global data from file\n');
G_ = getpref('Rafael', 'G_');
else % Running the first time:
G_.pi = 3.14;
G_.imag = 1i;
G_.PIN = 5553;
end
mlock; % Block "clear all" to delete G_
end
if nargin == 2
G_.(Name) = Value;
elseif nargin == 1
if strcmpi(Name, 'save')
fprintf('::: Saving global data to file\n');
setpref('Rafael', 'G_', G_);
elseif strcmpi(Name, 'load')
G_ = getpref('Rafael', 'G_');
else
error('Rafael:YourGlobalFcn:BadCommand', ...
'Unknown command: %s', Name);
end
end
G = G_;
end
Now insert "YourGlobalFcn('save')" to your "finish.m" file. Then G_ is stored persistently between Matlab sessions and restored automatically.
But again: Running e.g. two Matlab sessions can cause conflicts and you cannot control, in which one the last changes have been made. Use it with care: All methods to store data globally can drill a hole in your knee. Storing parameters individually e.g. for each instance of a GUI or for each Matlab session might be useful. But this depends on your code also.
Rafael Kübler
Rafael Kübler 2017년 11월 29일
Thanks. This works for me.
Steven Lord
Steven Lord 2017년 11월 29일
"All methods to store data globally can drill a hole in your knee."
I've never heard the caution against global variables described using that particular expression before. It gets the message across quite vividly, though. Yikes.
Is it possible to create a struct with more level? for example:
G_.Number.pi
G_.Number.imag
G_.Strings.Name
and then acces it something like:
G_.(Name1).(Name2)
Stephen23
Stephen23 2017년 11월 29일
Yes. Try it.
Rafael Kübler
Rafael Kübler 2017년 11월 30일
Oh, yes it works however now.

댓글을 달려면 로그인하십시오.

추가 답변 (3개)

Jos (10584)
Jos (10584) 2017년 11월 29일

0 개 추천

Take a look at the setappdata and getappdata. You can use the root handle to store variables.
setappdata(0,'MyVar',1:10)
per isakson
per isakson 2017년 11월 29일
편집: per isakson 2017년 11월 29일

0 개 추천

Download parse_pv_pairs by John D'Errico and run this example
preference.Viscosity = 1;
preference.Volume = 1;
preference.Pie = 3.141592653589793;
preference.Description = 'test';
params = examplefun( preference, 'Viscosity',2, 'Volume',3 );
and inspect params
>> params
params =
Viscosity: 2
Volume: 3
Pie: 3.1416
Description: 'test'
where
function ip = examplefun( nv, varargin )
ip = parse_pv_pairs( nv, varargin );
end
In examplefun you refer to the input arguments as ip.Viscosity, ip.Volume, ip.Pie and ip.Description.
This example doesn't fully meet your requirements, since the structure, preference, must contain all fields.
This solution may be developed further. Download CATSTRUCT, by Jos (10584) and run this modified example
preference.Viscosity = 1;
preference.Pie = 3.141592653589793;
params = examplefun( preference, 'Viscosity',2 );
and inspect params carefully
params =
Description: 'Default values'
Pie: 3.1416
Viscosity: 2
Volume: 12
>>
where
function ip = examplefun( nv, varargin )
warning('off','catstruct:DuplicatesFound')
default.Viscosity = 11;
default.Volume = 12;
default.Pie = 3.141592653589793;
default.Description = 'Default values';
nv = catstruct( default, nv );
ip = parse_pv_pairs( nv, varargin );
end
Both these FEX-contributions are good.

댓글 수: 1

Rafael Kübler
Rafael Kübler 2017년 11월 29일
Than you very much Per for your answer, but i think i stick with Jans' solution.

댓글을 달려면 로그인하십시오.

카테고리

도움말 센터File Exchange에서 Scope Variables and Generate Names에 대해 자세히 알아보기

질문:

2017년 11월 29일

댓글:

2017년 11월 30일

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by