为什么这两个脚本实例的表现不同?

时间:2016-09-02 14:46:33

标签: performance matlab optimization multidimensional-array

我有2个实现算法的实例,我希望它尽可能快,因为它将成为我需要重复多次的例程的一部分。

我的想法如下:我有n n mc矩阵(称之为m)并基于此我必须创建n 1}} z矩阵(称之为z)。 n的每一行都是将前一行乘以n c clear all x = -5:.02:5; w = 1:.02:11; t(1,1,:) = w; n = length(x); m = length(w); z = zeros(m,n); z(1,:) = exp(-x.^2/2)/sqrt(2*pi); a = bsxfun(@times,x,t); b = bsxfun(@minus,a,x'); c = exp(-bsxfun(@rdivide,b.^2,2*t)); for i = 2:m z(i,:) = z(i-1,:)*squeeze(c(:,:,i)); z(i,:) = z(i,:)/trapz(x,z(i,:)); end 切片clear all x = -5:.02:5; t = 1:.02:11; n = length(x); m = length(t); z = zeros(m,n); z(1,:) = exp(-x.^2/2)/sqrt(2*pi); for i=2:m c = exp(-(bsxfun(@minus,x*t(i),x')).^2/(2*t(i))); z(i,:) = z(i-1,:)*c; z(i,:) = z(i,:)/trapz(x,z(i,:)); end 并将其标准化的结果。

我认为在matlab中总是最好对代码进行矢量化并尽可能避免循环,所以我认为第一种方法是我能想到的最快的方法。但事实证明,第二次实施的速度提高了约15%。谁能解释我为什么?另外,你能否告诉我,我是否可以做得比第二种选择更好?

以下是两个脚本的虚拟版本(足够用于说明目的)

脚本1

z(i,:) = z(i-1,:)*squeeze(c(:,:,i));

脚本2

$(document).on('click','#add_free_ticket',function(e){
    e.preventDefault();
    $("#tab_logic").append('<tr id="free_event_clone"><td class="form-group"><input type="text" name="free_ticket_name[]" class="form-control"></div></td><td class="form-group"><input type="text" name="free_ticket_avail[]" class="form-control"></td><td class="form-group"><select class="form-control" name="free_ticket_avail_to[]"><option value="0" selected>All</option><option value="1">Members Only</option></select></td><td class="form-group"><input type="text" name="free_ticket_frm_date[]" class="form-control datetimepicker1"></td><td class="form-group"><input type="text" name="free_ticket_to_date[]"  id="tmp2" class="form-control datetimepicker2"></td><td class="form-group"><input type="text" name="free_ticket_per_guest[]" value="1" class="form-control"></td><td><button class="del_free_ticket  btn btn-danger btn-sm">X</button></td></tr>');
}  

我没想到脚本1中的这一行

my_app_folder

要尽可能慢。

1 个答案:

答案 0 :(得分:1)

迭代完成索引到ndim数组可能会很昂贵。因此,我们可以使用 scratchpad-variable 来避免这种情况。因此,我们可以将script #2修改为类似的内容 -

z      = zeros(m,n);
tmp    = exp(-x.^2/2)/sqrt(2*pi);
z(1,:) = tmp;
for i=2:m
    tmp = tmp*exp(-(bsxfun(@minus,x*t(i),x')).^2/(2*t(i)));
    tmp = tmp/trapz(x,tmp);
    z(i,:) = tmp;
end

tmp变量是此处使用的暂存器变量。此外,我们正在将bsxfun(@minus结果作为c提前直接输入到下一步。

运行时测试 -

输入:

x = -5:.04:5;
t = 1:.04:11;

时间:

--------------------- With Script #2
Elapsed time is 0.571562 seconds.
--------------------- With Optimized Script
Elapsed time is 0.478028 seconds.

那么,那里有一些微小的改善。