<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />我有一個 JMP 腳本來提示用戶輸入目錄,然後從該目錄中過濾特定的文件類型。我的問題是過濾過程通常比獲取文件花費的時間更長。如果文件數量較大(>100,000 個文件),則收集和過濾文件的總時間可能會超過 30 分鐘。有沒有更快或更有效的方法來做到這一點?我正在使用 JMP11。謝謝!
// 例子。
名稱默認為此處( 1 );
dir = 選擇目錄( "選擇目錄", "/C:/Program Files/SAS/" );
t1 = 滴答秒();
文件=目錄中的文件(dir,遞歸);
t2 = 滴答秒();
t_getfiles = t2 - t1;
n_getfiles = N 個項目( 文件 );
t3 = 滴答秒();
For( i = N 個項目( 文件 ), i >= 1, i--,
If( !Ends With( 文件,“.jmp”),
從(文件,i)中刪除
)
);
t4 = 滴答秒();
t_filterfiles = t4 - t3;
n_filterfiles = N 個項目(文件);
顯示( t_getfiles, n_getfiles, t_filterfiles, n_filterfiles );
第一個示例在 JMP 12 中要快得多(與數據表示例的速度相似);它似乎仍在 JMP 11 中表現出一些 N^2 行為。
是的,重新設計過濾循環以刪除 N^2 行為。JSL {lists} 從前面開始訪問元素。您從後面開始,以防止刪除的元素弄亂索引。這導致了操作列表時幾乎最壞情況的時間行為,遍歷 i 個元素以到達第 i 個元素。這是一個重新設計的版本,它從文件列表中刪除最前面的元素,檢查它,然後將其插入作為過濾列表的最前面的元素。
dir = "c:\";
t1 = Tick Seconds();
files = Files In Directory( dir, Recursive );
t2 = Tick Seconds();
t_getfiles = t2 - t1;
n_getfiles = N Items( files );
filteredFiles = {};
t3 = Tick Seconds();
while( (testname = Remove From( files, 1 )) != {},
If( Ends With( testname[1], ".jmp" ),
insertinto(filteredFiles,testname,1);
)
);
t4 = Tick Seconds();
t_filterfiles = t4 - t3;
n_filterfiles = N Items( filteredFiles );
Show( t_getfiles, n_getfiles, t_filterfiles, n_filterfiles );
t_getfiles = 4.0333333333333;
n_getfiles = 171630;
t_filterfiles = 258.5;
n_filterfiles = 975;
大約5分鐘。
另一個想法:您可以像這樣加載數據表:
dir = "c:\";
t1 = Tick Seconds();
files = Files In Directory( dir, Recursive );
t2 = Tick Seconds();
t_getfiles = t2 - t1;
n_getfiles = N Items( files );
t3 = tickseconds();
dt = New Table( "directory",
Add Rows( 0 ),
New Column( "filename", Character, Nominal, Set Values( files ) ),
New Column( "isTable",
Numeric,
Continuous,
Format( "Best", 12 ),
Formula( Ends With( :filename, ".jmp" ) )
)
);
dt<
dt<
dtFiltered = dt<
t4=tickseconds();
t_filterfiles = t4 - t3;
n_filterfiles = N rows( dtFiltered );
Show( t_getfiles, n_getfiles, t_filterfiles, n_filterfiles );
t_getfiles = 4.01666666666642;
n_getfiles = 171635;
t_filterfiles = 0.716666666666697;
n_filterfiles = 975;
大約5秒。<