MATLAB における Java の「同期」に相当するものは何ですか?
2 つのタイマーがあり、両方とも変数 (つまり、行列) M を変更できるとします。それらが同時に起動した場合、両方とも一度に M を変更しようとします (エラーが発生する可能性があります)。MATLAB はそのような操作を自動的に同期しますか?
MATLAB における Java の「同期」に相当するものは何ですか?
2 つのタイマーがあり、両方とも変数 (つまり、行列) M を変更できるとします。それらが同時に起動した場合、両方とも一度に M を変更しようとします (エラーが発生する可能性があります)。MATLAB はそのような操作を自動的に同期しますか?
Matlab は 99% がシングル スレッドです (残りの 1% はこの質問には関係ありません)。したがって、synchronized
キーワードは使用できません。
ただし、一部の操作は中断可能です。つまり、GUI コールバックまたはタイマーが予期しない時間に操作を一時停止する可能性があります。これにより、マルチスレッド システムで見られるのと同じ問題が発生する可能性があります。
中断を防ぐために、interruptible
プロパティが使用可能な場合 (通常は GUI オブジェクト上) に使用してください。これにより、GUI コールバックを処理する際の再入可能な動作を防止する必要性が処理されます。例えば
set(gcf,'Interruptible','off')
ただし、これはタイマーに関連する割り込みを処理しません。
2 つのタイマーは互いに割り込むことができないように見えるため、同期は必要ありません。ただし、タイマーはメイン アクティビティを中断できます。
いくつかのテストの後、これはpause
、drawnow
、figure
、またはgetframe
呼び出しの近くで発生する可能性があり、これはドキュメントで暗示されています。また、一部の tic/toc 呼び出しや Java への呼び出しなど、他の呼び出しの近くで発生することもあります。
Interruptible
必要になるかもしれませんが、タイマーまたは関数のプロパティとの類似点を認識していません。ルート オブジェクト0
にはInterruptible
プロパティがありますが、効果はありません (ドキュメントごとに確認済み)。
注:これは私が提供した以前の回答(履歴を参照)からの大きな変更であり、最近の学習を表しています。前の例では 2 つのタイマーを使用していましたが、これらは互いに競合していないように見えます。この例では、1 つのタイマーとメイン関数の操作を使用しています。
以下に例を示します。1 つの中断できないケースと、関数some_work
が中断される 2 つのケースを示しています。
function minimum_synchronization_example
%Defune functions to test for interruptability
%(these are all defined at the bottom of the file)
fnList = {
@fn_expectedNoInterruption
@fn_expectedInterruption
@fn_unexpectedInterruption
};
for ix = 1:length(fnList)
disp(['---Examples using ' func2str(fnList{ix}) '--------'])
test_subfunction_for_interrupt_allowed(fnList{ix});
end
end
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function test_subfunction_for_interrupt_allowed(fn)
%Setup and start a timer to execute "some_work"
t1 = timer();
set(t1,...
'Name','PerformSomeWorkTimer1', ...
'TimerFcn', @(~,~) some_work('Timer-1', fn), ...
'ExecutionMode','fixedSpacing', ...
'Period', 0.4, ...
'TasksToExecute', 6, ...
'BusyMode', 'drop')
start(t1);
%Then immediately execute "some_work" from the main function
for ix = 1:6
some_work('MainFun', fn);
pause(0.2);
end
%The timer and the loop take about the same amount of time, stop and delete
%the timer before moving on
stop(t1);
delete(t1);
end
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function some_work(displayString, subFunctionWhichMayAllowInterrupts)
%Initialize persistent, if needed.
%This records then umber of active calls to this function.
persistent entryCount
if isempty(entryCount)
entryCount = 0;
end
%Record entry
entryCount = entryCount+1;
tic;
%Perform some work (Inverting a 3000-by-3000 matrix takes about 1 sec on my computer)
[~] = inv(randn(3000));
%Run subfunction to see if it will be interrupted
subFunctionWhichMayAllowInterrupts();
%Display results. How many instances of this function are currently active?
if entryCount>1;
strWarning = 'XXX ';
else
strWarning = ' ';
end
disp([strWarning ' <' sprintf('%d',entryCount) '> [' displayString '] ; Duration: ' sprintf('%7.3f',toc)]);
%Record exit
entryCount = entryCount-1;
end
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function fn_expectedNoInterruption
x = 1+1;
end
function fn_expectedInterruption
drawnow;
end
function fn_unexpectedInterruption
m = java.util.HashMap();
end