目录
前言
本文不刻意区分MatLab中的"矩阵"和"数组"
前文摘要:从C++到MatLab
MatLab数据存储、运算、传输单位是数组,很多函数的返回值也是数组
向量(一维数组)和矩阵(二维数组)是MatLab最常用的数组
向量可以看做行矩阵或列矩阵,标量可以看做只有一个元素的特殊矩阵
MatLab是强大的数学建模工具,但也只是工具,没有必要在概念上浪费太多时间,会用才是目的
1.新建标量、向量和矩阵
例:新建标量的指令
>> a = 5.4
例:新建行向量的指令
>> b = [1, 2, 3]
>> b = [1 2 3]
空格和半角逗号对行向量是等价的
例:混用空格和半角逗号(不建议)
>> A = [1, 2 3, 4 5]
例:新建列向量的指令
>> b = [1; 2; 3]
输出:
b =
1
2
3
例:新建矩阵的指令
>> A = [1, 2, 3; 4, 5, 6]
输出:
A =
1 2 3
4 5 6
在输入矩阵时,半角分号相当于换行符
MatLab矩阵以行向量为单位输入,以列向量为单位存储
建议:输入行向量或矩阵时,同行元素统一用半角逗号隔开
2.矩阵的快速创建
递增/递减型向量的创建
1)生成线性等距的行向量的快捷命令
>> a : b : c
a是起始值,b是步长,c是终止值
例:
>> 1 : 1 : 5
输出:
ans =
1 2 3 4 5
注意:步长可以为负值,但步长不能为0!
当终止值和起始值的差不能被步长整除时,生成的行向量会被提前截止
例:
>> 1 : 2 : 8
输出:
ans =
1 3 5 7
通过此例可知,终止值c可能不被生成的行向量包含
步长值可以省略不写,默认的步长值为1
例:
>> 1 : 5
输出:
ans =
1 2 3 4 5
2)生成线性等距的行向量的函数
>> linspace(a, c, n)
a是起始值,c是终止值,n是生成的元素个数
和快捷命令不同,调用linspace()函数生成的行向量,终止值c一定会被生成的向量包含
例:
>>linspace(1,5,5)
输出:
ans =
1 2 3 4 5
例:
>> linspace(1, 6, 5)
输出:
ans =
1.00 2.25 3.50 4.75 6.00
可以看出终止值一定会被生成的行向量包含
如果a==c,则生成向量的每个元素值都是a
例:
>> linspace(1, 1, 4)
输出:
ans =
1 1 1 1
3)生成对数等距的行向量的函数
>> logspace(a, c, n)
a是起始值的10的对数,c是终止值的10的对数,n是生成的元素个数
对数等距的行向量,通俗来讲就是等比数列
例:
>> logspace(0, 3, 4)
输出:
ans =
1 10 100 1000
注意:logspace()函数前两个参数是10的对数,不是值本身
也就是说可以把logspace(0, 3, 4)的执行看做两步
第一步:生成对数行向量[0 1 2 3]
第二步:生成行向量[10^0 10^1 10^2 10^3]
可以生成向量和矩阵的库函数
包括但不限于:
diag() //生成对角矩阵,或取出矩阵的对角元素
eye() //生成单位矩阵
ones() //返回全一矩阵
zeros() //返回全0矩阵
由于MatLab函数重载非常多,具体功能请自行上机尝试
3.矩阵元素的编址和寻访
矩阵元素的编址方式
1)下标编址
例:A(2,1)表示矩阵A第2行第1列的元素
注意:MatLab中的下标从1开始
2)序号编址
序号为i的元素,是指从上到下,从左到右的第i个元素
例:
>> A = [1, 2, 3; 4, 5, 6; 7, 8, 9]
>> A(4)
输出:
A =
1 2 3
4 5 6
ans =
2
注意:序号访问是一列一列访问的,而不是一行一行访问的
矩阵元素的寻访方式:
这部分内容强烈建议上机实验
1)按地址寻访:下标寻访和序号寻访
下标寻访
>> A(r, c)
r和c可以是标量,也可以是向量
例:r和c是向量时地址寻访的返回值
>> A = [1, 2, 3; 4, 5, 6; 7, 8, 9];
>> A([1, 3], [1, 3])
输出:
ans =
1 3
7 9
可以看出,返回A的第1,3行,第1,3列上的元素组成的子矩阵
前文提到了"生成线性等距的行向量的快捷命令"
可以通过冒号快捷命令生成的行向量进行矩阵下标寻访
例:
>> A = [1, 2, 3; 4, 5, 6; 7, 8, 9];
>> A(1:2, 2:3)
输出:
ans =
2 3
5 6
当访问矩阵全部行的某一列元素,或全部列的某一行元素时,冒号快捷命令可以进一步简写
例:
>> A(2, :) //访问矩阵A的第2行所有元素
>> A(:, 2) //访问矩阵A的第2列所有元素
序号寻访
>> A(id)
id可以是标量,也可以是向量
例:
>> A = [1, 2, 3; 4, 5, 6; 7, 8, 9];
>> A([1, 3, 6])
输出:
ans =
1 7 8
A([1, 3, 6])访问的是A的第1, 3, 6号元素
冒号快捷命令的序号寻访
例:
>> A = [1, 2, 3; 4, 5, 6; 7, 8, 9];
>> A(2:6)
输出:
ans =
4 7 2 5 8
当按序号访问矩阵的所有元素时,会返回一个列向量
例:
>> A = [1, 2, 3; 4, 5, 6; 7, 8, 9];
>> A(:)
输出:
ans =
1
4
7
2
5
8
3
6
9
2)按条件寻访
>> A(Alo)
A是被寻访的矩阵,Alo是由逻辑值0/1 组成的条件矩阵(logical矩阵)
逻辑1对应的位置会被寻访,逻辑0对应的位置不会被寻访
注意:logical矩阵由逻辑运算生成,后文会提到
例:
>> A = [1, 2, 3; 4, 5, 6; 7, 8, 9];
>> L = (A >= 6)
>> A(L)
输出:
L =
0 0 0
0 0 1
1 1 1
ans =
7
8
6
9
4.矩阵的双目运算
“标量运算”
这是笔者自己起的名字
矩阵的"标量运算"是指单纯把矩阵中的元素当做独立的标量来运算
"标量运算"的规则如下:
① A # B = [aij # bij] = [cij],A和B都是矩阵
② A # n = [aij # n] = [cij],A是矩阵,n是标量
'#'代表服从"标量运算"规则的运算符
例:矩阵的加法,矩阵的减法,都是服从"标量运算"规则的,而矩阵乘法不符合"标量运算"规则
规则②的意思是,标量和矩阵的运算等价于标量与每个矩阵元素进行运算
服从"标量运算"规则的运算符如下:
算术运算:
+ - .*(标量乘) .\和./(标量左除和右除) .^(标量幂)
注意:标量乘法、除法和幂,要在运算符左边加半角点’.’
矩阵的标量除法,左除和右除等价
关系运算:
> < >= <= == ~=(不等于)
注意:MatLab的不等于不是"!="
逻辑运算:
& | ~(非) xor(异或)
注意:逻辑非是’~’,而不是’!’
异或是函数,不能写成A xor B,应该写成xor(A,B)
矩阵"标量运算"的优先级:算术运算>关系运算>逻辑运算
MatLab中的部分初等函数可以对矩阵进行"标量运算"
例:sin()函数的参数可以是一个矩阵,返回值是一个同等规模的矩阵
sin(A) = sin([aij]) = [sin(aij)] = [bij] = B
矩阵运算
*(矩阵乘) \ (矩阵左除)和/(矩阵右除) ^(矩阵幂)
矩阵左除和右除的区别:
矩阵除法等价于乘分母的逆矩阵
即:A / B = A * inv(B),inv(B)代表矩阵B的逆
但是矩阵乘法没有交换律:A * B = B * A不一定成立
所以A除B到底应该表示成A * inv(B)还是inv(B) * A?
作以下规定:
左除\:B \ A = inv(B) * A
右除/:A / B = A * inv(B)
注意:左除的分母写在左边,实际上B\A看上去B也是在分数线下面
建议:如果矩阵B是满秩的,用逆矩阵乘法,代替矩阵除法
矩阵幂的两种形式:
底数为矩阵,指数为标量
A ^ n = A · A · A…A(n个A矩阵乘)
线性代数指出:上述运算可以简化
对A作对角化,找到可逆矩阵Q,使A = Q · A’ · inv(Q)
其中A’是由A的特征值组成的对角矩阵,inv(Q)是Q的逆
A ^ n = Q · (A’ ^ n) · inv(Q),由于对角矩阵的幂十分好求,所以可以快速得出矩阵A的n次幂
A’ = diag(x1, x2, x3, …)
A’ ^ n = diag(x1 ^ n, x2 ^ n, x3 ^ n, …)
底数为标量,指数为矩阵
规定n ^ A的运算规则如下:
同理,对A作对角化,找到可逆矩阵Q,使A = Q · A’ · inv(Q)
A’ = diag(x1, x2, x3, …)
n ^ A = Q · diag(n ^ x1, n ^ x2, n ^ 3, …) · inv(Q)
两种矩阵幂的运算方式相似
矩阵函数
矩阵函数的运算过程和矩阵幂的相似
矩阵函数f(A)的运算模板:
对A作对角化,找到可逆矩阵Q,使A = Q · A’ · inv(Q)
A’ = diag(x1, x2, x3, …)
f(A) = Q · diag(f(x1), f(x2), f(x3), …) · inv(Q)
例:矩阵指数函数expm(A)
expm(A) = Q · diag(exp(x1), exp(x2), exp(x3), …) · inv(Q)