MATLAB®对涉及矩阵和向量的操作进行优化。调用了修正基于循环、面向标量的代码来使用MATLAB进行矩阵和向量运算的过程向量化.向量化代码是值得的,原因如下:
外观:向量化的数学代码更像教科书中的数学表达式,使代码更容易理解。
不容易出错没有循环,向量化代码通常更短。更少的代码行意味着引入编程错误的机会更少。
性能:向量化代码的运行速度通常比相应的包含循环的代码快得多。
这段代码计算从0到10的1001的正弦值:
我= 0;为t = 0:。01:10 I = I + 1;y (i) =罪(t);结束
这是同一代码的矢量化版本:
t = 0: .01:10;y =罪(t);
第二个代码示例的执行速度通常比第一个代码示例快,并且是对MATLAB的更有效的使用。通过创建包含所示代码的脚本,测试系统上的执行速度,然后使用抽搐
和toc
函数度量它们的执行时间。
这段代码计算向量每5个元素的累积和:
x = 1:1;Ylength = (length(x) - mod(length(x),5))/5;y (1: ylength) = 0;为N = 5:5:length(x) y(N /5) = sum(x(1: N));结束
使用矢量化,可以编写一个更简洁的MATLAB过程。这段代码显示了一种完成任务的方法:
x = 1:1;xsums = cumsum (x);y = xsums(5:长度(x));
数组操作符对数据集中的所有元素执行相同的操作。这些类型的操作对于重复计算是有用的。例如,假设您收集卷(V
),以记录它们的直径(D
)及身高(H
).如果你只收集一个圆锥的信息,你就可以计算出这个圆锥的体积:
V = 1/12 *π* (D ^ 2) * H;
现在,收集10000个视锥细胞的信息。向量D
和H
每个元素包含10000个元素,你想要计算10000个体积。在大多数编程语言中,你需要设置一个类似于以下MATLAB代码的循环:
为n = 1:10000 V(n) = 1/12*pi*(D(n)^2)*H(n)结束
使用MATLAB,你可以用与标量情况相似的语法对向量的每个元素执行计算:
%矢量化计算V = 1/12 *π* (d . ^ 2)。* H;
请注意
加句号(.
)在操作符之前*
,/
,^
,将它们转换为数组操作符。
数组操作符还使您能够组合不同维数的矩阵。这种大小为1的维度的自动扩展对于向量化网格创建、矩阵和向量操作等等都很有用。
假设矩阵一个
表示考试成绩,其中的行表示不同的班级。你要计算每个班级的平均分数和个人分数之间的差值。使用循环,操作看起来像:
A = [97 89 84;95 82 92;64 80 99;76 77 67;...88 59 74;78 66 87;55 93 85);马=意味着(A);B = 0(大小(A));为n = 1:size(A,2) B(:,n) = A(:,n) - mA(n);结束
更直接的方法是用——意思是()
,它避免了循环的需要,而且速度快得多。
devA = A - mean(A)
devA = 18 11 0 16 4 8 -15 2 15 -3 -1 -17 9 -19 -10 -1 -12 3 -24 15
尽管一个
是一个7 × 3矩阵吗意思是(A)
是一个1乘3的向量,MATLAB隐式地扩展向量,就好像它有与矩阵相同的大小,并且操作执行作为一个正常的元素减操作。
操作数的大小要求是,对于每个维度,数组要么具有相同的大小,要么其中一个为1。如果满足这个要求,则将其中一个数组的大小为1的维度展开为与另一个数组中相应维度的大小相同。有关更多信息,请参见基本操作的兼容数组大小.
隐式展开对向量化有用的另一个领域是在处理多维数据时。假设你想对一个函数求值,F
,两个变量,x
和y
.
F (x, y) = x * exp (- x2- y2)
求函数在每个点的组合处的值x
和y
向量,你需要定义一个值网格。对于这个任务,您应该避免使用循环来遍历点组合。相反,如果一个向量是列,另一个是行,那么当向量与数组操作符一起使用时,MATLAB会自动构建网格,例如x + y
或x - y
.在这个例子中,x
是一个21乘1的向量吗y
是一个1 × 16的向量,所以这个操作通过展开第二个维度得到一个21 × 16的矩阵x
第一个维度y
.
x =(2:0.2:2)”;% 21-by-1y = -1.5:0.2:1.5;% 1-by-16F = x。* exp (- x ^ 2 y ^ 2);% 21-by-16
数组批量处理的逻辑扩展是向量化比较和决策。MATLAB比较运算符接受向量输入并返回向量输出。
例如,假设在收集10,000个锥的数据时,您记录了一些直径的负值。属性可以确定向量中的哪些值有效>=
接线员:
D = [-0.2 1.0 1.5 3.0 -1.0 4.2 3.14];D > = 0
Ans = 0 1 1 1 0 1 1
Vgood
,对应的元素D
都是非负的。Vgood = V(D >= 0);
MATLAB允许您使用函数对整个向量的元素执行逻辑与或或运算所有
和任何
,分别。如果所有的值都是D
零度以下:
如果所有(D < 0)警告(“所有直径值都是负数。”)返回结束
MATLAB还可以比较两个大小一致的向量,允许您施加进一步的限制。这段代码找到所有V是非负的值D
大于H
:
V((V >= 0) & (d > h))
为了便于比较,MATLAB包含特殊的值来表示溢出、下溢和未定义的操作符,例如正
和南
.逻辑运算符isinf
和isnan
存在的目的是帮助对这些特殊值执行逻辑测试。例如,排除通常是有用的南
从计算值:
x = [2 -1 0 3 NaN 2 NaN 11 4 Inf];xvalid = x (~ isnan (x))
xvalid = 2 -1 0 3 2 11 4 Inf
请注意
正= =正
返回true;然而,南= =南
总是返回false。
在向量化代码时,您经常需要构造一个具有特定大小或结构的矩阵。存在创建统一矩阵的技术。例如,你可能需要一个元素相等的5 × 5矩阵:
一个= 1 (5,5)* 10;
v = 1:5;一个= repmat (v, 3,1)
A = 1 2 3 4 5 1 2 3 4 5 1 2 3 4 5
这个函数repmat
具有从较小的矩阵或向量构造矩阵的灵活性。repmat
通过重复输入矩阵创建矩阵:
A = repmat(1:3,5,2);3, 2, 2)
A = 1 2 3 1 2 3 1 2 3 1 2 3 1 2 3 1 2 3 1 2 3 1 2 3 1 2 3 1 2 3 1 2 3 1 2 3 1 2 3 1 2 3 1 2 3 1 2 3 1 2 3 1 2 3 1 2 3
在许多应用中,对一个向量的一个元素所做的计算依赖于同一向量中的其他元素。例如,一个向量,x,可能代表一个集合。如何迭代通过一个集合没有为
或而
循环并不明显。当您使用向量化的代码时,这个过程会更加清晰,语法也不会那么麻烦。
求向量的冗余元素有许多不同的方法。一种方法涉及到函数diff
.在对向量元素进行排序之后,当使用diff
函数在这个向量上。因为diff (x)
生成一个元素比x
,则必须添加一个不等于集合中任何其他元素的元素。南
总是满足这个条件。最后,你可以使用逻辑索引来选择集合中唯一的元素:
X = [2 1 2 2 3 1 3 2 1 3];x = (x);差异= diff ([x,南]);y = x(区别~ = 0)
Y = 1 2 3
独特的
功能:y =独特(x);
独特的
函数可能提供比所需更多的功能,并减慢代码的执行。使用抽搐
和toc
函数,如果您想要测量每个代码段的性能。
而不仅仅是返回的集合或子集x
,可以计算元素在向量中出现的次数。在向量排序之后,可以使用找到
函数来确定中零值的指标diff (x)
以及显示元素改变值的位置。的后续索引之间的差异找到
函数指示特定元素的出现次数:
X = [2 1 2 2 3 1 3 2 1 3];x = (x);差异= diff ([x,马克斯(x) + 1]);y = x(find(1,difference))
y = 1 y = 1 y = 1
找到
函数没有返回索引南
元素。你可以数一数南
和正
值使用isnan
和isinf
功能。
count_nans =总和(isnan (x (:)));count_infs =总和(isinf (x (:)));