可能な場合は[元に戻す](Undo)を使用不可にする
[元に戻す](undo)機能によって多くのメモリが消費され、処理が遅くなることがあります。
-
リスナーから実行する MAXScript コマンド。スクリプト エディタまたはマクロ スクリプトは、[元に戻す](undo)がオンであるコンテキストで実行されます。
-
スクリプト UI コントロールから実行する MAXScript コマンドは、[元に戻す](undo)がオンであるコンテキストで実行されません。
-
[元に戻す](undo)がオンの状態でノードを作成し、[元に戻す](undo)がオンの状態でノードに何かを実行した場合は、[元に戻す](undo)がオフの状態でノードを削除しないでください。
-
メッシュを使用して作業する場合は、通常、[元に戻す](undo)と[やり直し](redo)をサポートする meshop メソッドを使用します。しかし、通常はループのすべての操作で元に戻すレコードを保存する必要はなく、最初と最後のレコードを保存する必要しかありません。
-
EPoly を使用して作業する場合は、ループのすべての操作で元に戻すレコードを保存する必要があります。
テスト ケース:
|
em = mesh()
meshop_setvert = meshop.setvert
fn test7 holdAll =
(
local nVerts = getnumverts em
for i = 1 to nVerts do
with undo (holdAll or (i == 1 or i == nVerts))
meshop_setvert em i ([1,1,1]*i)
)
|
100,000 回の繰り返しの場合
|
test7 true -- 85313 msec., 229 MB
test7 false-- 7609 msec., 11 MB
|
undo レコードを作成するすべての操作は、変更されたオブジェクトの内部コピーを作成して後で元に戻せるようにするため、時間とメモリを消費します。複数オブジェクトをまとめてアタッチするなど、ループ内で複数の変更を加える場合、[元に戻す](Undo)機能では生成されるオブジェクトごとに
1 つの undo コピーを作成しようとするためメモリが不足する可能性があります。[Undo off ()] コンテキストを使用して明示的に[元に戻す](Undo)機能を無効にすると、このような場合にスクリプトの速度を大幅に向上する手助けとなります。
undo
次の例でこの違いを示します。どちらの場合も、MAXScript を使用して 1000 個のボックスを作成してから attach 関数を使用して 1 つのメッシュにアタッチします。最初の例では、既定値によって
attach 呼び出しごとに 1 つの undo レコードが生成されます。2 番目の例では、[元に戻す](undo)機能は明示的に使用不可にされます。
例 1 - 最適化されていないスクリプト:
|
delete $Box*--delete any existing boxes
box_array = #()--initialize an array
for i = 1 to 1000 do--repeat 1000 times
box_array[i] = box pos:[i*30,0,0]--create 1000 boxes
st = timestamp()--get the start time in milliseconds
master_box = convertToMesh box_array[1]--collapse the first box to mesh
for i = 2 to 1000 do--go through all other boxes
attach master_box box_array[i]--attach each box to the mesh
et = timestamp()--stop the time
print (et-st)--print the resulting time
gc()--call Garbage Collection &endash; you will needed it!
|
800MHz の PC では、スクリプトのアタッチ部分の実行に 1 分以上かかりました。これは主に、システムのメモリが不足して OS がディスクにスワップする必要があったためです。3ds Maxのメモリ使用量は約 300 MB に達しました。
|
例 2 - 最適化されているスクリプト:
|
delete $Box*
box_array = #()
for i = 1 to 1000 do
box_array[i] = box pos:[i*30,0,0]
st = timestamp()
undo off--the only difference - the undo
(--has been turned off
master_box = convertToMesh box_array[1]
for i = 2 to 1000 do
attach master_box box_array[i]
)--end undo off
et = timestamp()
print (et-st)
--call Garbage Collection - you will needed it!
|
同じ 800MHz のマシンでスクリプトのアタッチ部分の実行に 3685 ミリ秒しか、かかりませんでした。約 20 倍も速度が向上しています。Windows の[タスク
マネージャ](Task Manager)ではメモリ消費量の変化はありませんでした。
|
前のヒント
シーン オブジェクトに変更を加えるときに、[ビューポートの再描画](Viewport Redraws)を使用不可にする
次のヒント
[修正](Modify)パネルの速度が低下する可能性 - 可能な場合は[作成](Create)パネルに変更する