/ 写在前面 – 我热爱技术、热爱开源。我也相信开源能使技术变得更好、共享能使知识传播得更远。但是开源并不意味着某些商业机构/个人可以为了自身的利益而一味地索取,甚至直接剽窃大家曾为之辛勤付出的知识成果,所以本文未经允许,不得转载,谢谢/


更改当前默认工作目录

使用 cd 命令即可:

  1. >> cd ~/Documents/MATLAB/

如下图:
image.png

搜索顺序

在提示符 >> 后输入一个名称,MATLAB将按照下列顺序执行搜索:

  1. 变量
  2. 内部函数
  3. 程序文件
    a. 当前文件夹下的程序文件
    b. 文件搜索路径文件夹中的程序文件

所以,在定义变量时,不要使用内部已经使用了的名称,比如 sin 这种内部函数名。但是如果使用了,而后面又要使用 sin 函数的话,在workspace里面删除 sin 变量即可。

设置搜索路径

方法1:

  1. >> path(path, 'D:\Documents')

方法2:
image.png

注意:如果当前文件夹和搜索路径文件下建立了一个同名的 .m 文件,当我们在命令行窗口输入文件名时,执行当前文件夹下的文件

数值数据

数值数据类型的分类:

  • 整型
  • 浮点型
  • 复数型

    整型

    整数又分为无符号和带符号的8、16、32、64位整数,共8种整数类型。

uint8 函数将数值数据转换为无符号8位整数, int8 函数将数值数据转换为带符号8位整数。

浮点型

浮点型数据分为单精度型(占4个字节)和双精度型(占8个字节)。

single 函数将其他类型的数据转换为单精度型, double 则转换为双精度型。

class 函数可以得到数据的类型。

  1. >> class(66)
  2. ans =
  3. 'double'

复数型

实部和虚部默认为双精度型。

MATLAB用 ij 来表示虚数单位。

  1. >> 6+5i
  2. ans =
  3. 6.0000 + 5.0000i
  4. >> 6+5j
  5. ans =
  6. 6.0000 + 5.0000i

对于复数型数据,可以使用 real 函数求复数的实部、 imag 函数求虚部。

数据操作

在MATLAB中,可以使用 format 命令来设置数值数据的输出格式。

  1. >> format long
  2. >> 5/3
  3. ans =
  4. 1.666666666666667
  5. >> format %回到默认输出格式short
  6. >> 5/3
  7. ans =
  8. 1.6667

注意: format 不影响数据的计算和存储。

三角函数默认以弧度为单位,若以角度为单位则需要在三角函数名后添加一个 d ,如 sind

  1. >> sin(pi/2)
  2. ans =
  3. 1
  4. >> sind(90)
  5. ans =
  6. 1

abs 函数可以求实数的绝对值、复数的模、字符串的ASCII码值。

  1. >> abs(-2)
  2. ans =
  3. 2
  4. >> abs(4+3i)
  5. ans =
  6. 5
  7. >> abs('a')
  8. ans =
  9. 97

用于取整的函数有:

  • fix :舍去小数取整
  • floor :“地板”,即向下取整
  • ceil :“天花板”,即向上取整
  • round :四舍五入取整

取余函数有 modrem ,当x和y的符号相同时,两个函数的结果一样;符号不同时,结果不同,此处以后再讨论。

MATLAB提供了判断素数的函数 isprime(n) ,当 n 是素数时返回1,否则返回0。

clear 函数清除workspace中的所有数据。

关于语句

MATLAB允许一行输入多个命令,此时可以用逗号 , 和分号 ; 来实现,区别在于使用逗号将会显示运行结果,而使用分号将隐藏运行结果。需要多行同时连续输入时,可用 Shift + Enter 来实现。

在一条语句后输入三个点 ... 表示我想换行,但还要继续输入语句。

在一条赋值语句后添加分号则表示不显示赋值后变量的结果,仅执行赋值操作。

在MATLAB中:

  • ans 是默认赋值变量
  • ij 代表虚数单位
  • pi 代表圆周率
  • NaN 代表非数,即Not a Number

关于 NaN 的运用,如果在绘图的时候,我们想裁掉一部分数据,那么我们只要把坐标上的这部分数据赋为 NaN 即可。

我们也可以在workspace中完成对变量的删除修改操作。

MATLAB提供了 whowhos 命令来查看在workspace中已经驻留的变量名清单,前者仅显示变量名,后者显示变量的详细信息。

内存变量 .mat 文件

.mat 文件(二进制格式)用于保存workspace中的变量:

  • save 命令:创建内存变量文件
  • load 命令:装入内存变量文件
    1. >> save myData x y ans% x, y, ans保存在myData.mat文件中
    2. >> load myData% 重新装载内存变量文件

    矩阵的建立

    直接输入法

  1. 将矩阵的元素用中括号括起来
  2. 同行元素用逗号空格分隔
  3. 不同行的元素之间用分号分隔
    1. >> A=[1,2,3;4 5 6;7,8,9]
    2. A =
    3. 1 2 3
    4. 4 5 6
    5. 7 8 9

    矩阵拼接

    1. >> A=[1,2,3;4 5 6;7,8,9]
    2. A =
    3. 1 2 3
    4. 4 5 6
    5. 7 8 9
    6. >> B=[-1,-2,-3;-4,-5,-6;-7,-8,-9]
    7. B =
    8. -1 -2 -3
    9. -4 -5 -6
    10. -7 -8 -9
    11. >> C=[A,B;B,A]
    12. C =
    13. 1 2 3 -1 -2 -3
    14. 4 5 6 -4 -5 -6
    15. 7 8 9 -7 -8 -9
    16. -1 -2 -3 1 2 3
    17. -4 -5 -6 4 5 6
    18. -7 -8 -9 7 8 9

    冒号表达式

    向量是矩阵的特例,使用冒号表达式可以产生行向量

冒号表达式的格式为 e1:e2:e3 ,其中:

  • e1 为初始值
  • e2 为步长,若省略则表示步长为1
  • e3 为终止值

在MATLAB中,还可以用 linspace(a,b,n) 函数产生行向量,其中:

  • a 是第一个元素
  • b 是最后一个元素
  • n元素总数,当 n 省略时,自动产生100个元素
  1. >> x=linspace(0,pi,6)
  2. x =
  3. 0 0.6283 1.2566 1.8850 2.5133 3.1416

结构矩阵和单元矩阵

结构矩阵见代码:

  1. >> student(1).no=001; student(1).name='senchun'; student(1).matrix=[11,12;21,22];
  2. >> student(2).no=002; student(2).name='nick'; student(2).matrix=[11,12;21,22];
  3. >> student
  4. student =
  5. 1×2 struct array with fields:
  6. no
  7. name
  8. matrix

单元数据类型也是把不同类型的数据放在一个变量中,但与结构矩阵所不同的是,结构矩阵的各个元素下还有成员,每个成员都有自己的名字,而单元矩阵的各个元素就是不同类型的数据,每个元素直接就是由不同类型的数据组成的。

注意,单元矩阵元素是用大括号括起来的。

  1. >> b={10,'senchun',[11,12;21,22];12,'nick',[1,2;3,4]}
  2. b =
  3. 2×3 cell array
  4. {[10]} {'senchun'} {2×2 double}
  5. {[12]} {'nick' } {2×2 double}

矩阵元素的引用

通过圆括号加下标来引用,比如 A(3,2) 就表示矩阵A的第3行、第2列的元素。

注意,在MATLAB中,如果赋值时行或列超过了原矩阵的行和列的大小,MATLAB就会自动扩展原来的矩阵,然后填充0。

  1. >> A=[1,2;3,4];
  2. >> A(3,1)=31
  3. A =
  4. 1 2
  5. 3 4
  6. 31 0

通过序号来引用就比较奇葩了,这里需要了解MATLAB是如何在内存中存放数据的。MATLAB的存储顺序不是按行来存储的,而是按列来存储的,即首先存储矩阵的第1列元素,然后第2列元素,……,一直到矩阵的最后一列元素。

矩阵元素的序号就是矩阵元素在内存中的排列顺序

  1. >> A=[1,2;3,4];
  2. >> A(3,1)=31
  3. A =
  4. 1 2
  5. 3 4
  6. 31 0
  7. >> A(4)% A(1)=1, A(2)=3, A(3)=31, A(4)=2
  8. ans =
  9. 2

这样,我们就不难得出(这个其实不用管):序号与下标是一一对应的,以m×n矩阵A为例,矩阵 A(i,j) 的序号为 (j-1)×m+i 。然后MATLAB还给了两个转换函数 sub2indind2sub ,这个暂时就先不用管了。

利用冒号表达式来获取子矩阵

  • A(i,:) 表示第 i 行的全部元素
  • A(:,j) 表示第 j 列的全部元素
  • A(i:i+m,k:k+m) 表示第 i~i+m 行内且在第 k~k+m 列中的所有元素
  • A(i:i+m,:) 表示第 i~i+m 行的全部元素

end 运算符

end 表示某一维的末尾元素下标。

  1. >> A=[1,2,3,4,5;6,7,8,9,10;11,12,13,14,15;16,17,18,19,20]
  2. A =
  3. 1 2 3 4 5
  4. 6 7 8 9 10
  5. 11 12 13 14 15
  6. 16 17 18 19 20
  7. >> A(end,:)
  8. ans =
  9. 16 17 18 19 20
  10. >> A([1,4],3:end)% 这里的[1,4]表示第1行和第4
  11. ans =
  12. 3 4 5
  13. 18 19 20

对矩阵动刀子

删除矩阵中的元素

可以利用空矩阵来删除矩阵的元素。

  1. >> A=[1,2,3,4;5,6,7,8;9,10,11,12]
  2. A =
  3. 1 2 3 4
  4. 5 6 7 8
  5. 9 10 11 12
  6. >> A(:,[2,4])=[]% 利用空矩阵来删除第2列和第4列的元素
  7. A =
  8. 1 3
  9. 5 7
  10. 9 11

重新塑造矩阵的形状

MATLAB提供了 reshape(A,m,n) 函数来改变矩阵的形状,即在矩阵总元素保持不变的前提下,将矩阵 A 重新排列成 m×n 的二维矩阵。但是要注意,该函数仅仅只是改变原矩阵的行数和列数,但并不改变原矩阵元素个数及其存储顺序(即先存放第1列,然后第2列,依此类推)。关于 reshape 函数的用法,以后有需要了再探讨。

  1. >> A=[1,2,3,4;5,6,7,8;9,10,11,12]
  2. A =
  3. 1 2 3 4
  4. 5 6 7 8
  5. 9 10 11 12
  6. >> A(:,[2,4])=[]
  7. A =
  8. 1 3
  9. 5 7
  10. 9 11
  11. >> B=A(:)% A(:)等价于reshape(A,6,1)
  12. B =
  13. 1
  14. 5
  15. 9
  16. 3
  17. 7
  18. 11

基本运算

MATLAB的运算都是针对矩阵而言的,包括算术运算、关系运算、逻辑运算。

基本算数运算

基本算数运算符: + (加)、 - (减)、 * (乘)、 / (右除)、 \ (左除)、 ^ (乘方)。

注意:

  1. 单个数据的算数运算只是矩阵运算的一种特例。
  2. 加减运算要求两矩阵同型。同时,一个标量也可以和矩阵进行加减运算,这时标量会和矩阵的每一个元素进行加减。
  3. 乘法运算要求两矩阵是可乘的,即前矩阵的列数等于后矩阵的行数。
  4. A 的平方 A^2 就是 A 乘上 A

除法运算

在MATLAB中,矩阵除法运算分为右除 / 和左除 \

如果A矩阵是非奇异方阵,即可逆的,则 B/A 等效于 B*inv(A)A\B 等效于 inv(A)*B

点运算

点运算符有: .*./.\.^

两个矩阵进行点运算是指它们的对应元素进行相关运算,要求两矩阵同型。

点运算比较具有MATLAB特色,在实际引用中起着很重要的作用,也是很多初学者容易弄混的一个问题。

关系运算

关系运算符有: <<=>>=== (等于)、 ~= (不等于)。

若关系成立,则关系表达式的结果为1,否则为0。

注意:

  1. 当参与比较的量是两个同型的矩阵时,比较是对两矩阵相同位置的元素按标量关系运算规则逐个进行的,最终的关系运算的结果是一个与原矩阵同型的矩阵,它的元素由0或1组成。
  2. 当参与比较的一个是标量,而另一个是矩阵时,则把标量与矩阵的每一个元素按标量关系运算规则逐个比较,最终的关系运算的结果是一个与原矩阵同型的矩阵,它的元素由0或1组成。

逻辑运算

逻辑运算符有: & (与)、 | (或)、 ~ (非)。

  1. a&b :a、b全为非零时,运算结果才为1,否则为0。
  2. a|b :a、b中只要有一个为非零,运算结果就为1。
  3. ~a :当a为零时,运算结果为1;当a为非零时,运算结果为0。

注意:

  1. 若参与逻辑运算的是两个同型矩阵,那么将对矩阵相同位置上的元素按标量规则逐个进行运算,最终运算结果是一个与原矩阵同型的矩阵,其元素由1或0组成。
  2. 若参与逻辑运算的一个是标量,而另一个是矩阵时,那么将在标量与矩阵中的每个元素之间按标量规则逐个进行运算,最终运算结果是一个与原矩阵同型的矩阵,其元素由1或0组成。

练习:寻找水仙花数

  1. clear;
  2. m=100:999;
  3. % ones
  4. m1=mod(m,10);
  5. % tens
  6. m2=mod(fix(m./10),10);
  7. % hundreds
  8. m3=fix(m./100);
  9. k=find(m==m1.^3+m2.^3+m3.^3);
  10. m(k)

&&|| 被称为 &| 的Short Circuit形式。

比如 A&B ,首先判断A的逻辑值,然后判断B的值,然后进行逻辑与的计算。

A&&B ,首先判断A的逻辑值,如果A的值为假,就可以判断整个表达式的值为假,就不需要再判断B的值。注意,A和B不能是矩阵,只能是标量。

||| 同理。

关于MATLAB中的 find 函数。

k = find(X) 返回一个包含数组 X 中每个非零元素的线性索引的向量。

  • 如果 X 为向量,则 find 返回方向与 X 相同的向量。
  • 如果 X 为多维数组,则 find 返回由结果的线性索引组成的列向量。
  • 如果 X 包含非零元素或为空,则 find 返回一个空数组。

    字符串处理

    在MATLAB中,字符串是用单引号括起来的字符序列。MATLAB把一个字符串当作一个行向量,这个行向量中每个元素对应一个字符,它的引用方法和数值向量是相同的。

注意,如果字符串中的字符含有单引号,那么这个单引号字符要用两个单引号来表示。

注意,字符串矩阵要求各行字符数要相等,否则会报错,不相等的用空格来填充,使它们的列数相同。

字符串的执行

eval(s) 函数把字符串参数 s 中的内容当作对应的MATLAB命令来执行。

字符串与数值之间的转换

absdouble 函数都可以用来获取字符串矩阵所对应的ASCII码数值矩阵。
char 函数可以把ASCII码矩阵转换为字符串矩阵。

  1. >> ch='MATLAB'
  2. ch =
  3. 'MATLAB'
  4. >> abs(ch)
  5. ans =
  6. 77 65 84 76 65 66
  7. >> char(abs(ch)+32)
  8. ans =
  9. 'matlab'

字符串的比较

有两种方法:利用关系运算符或字符串比较函数。

关系运算符比较:两个字符串里的每个字符依次按ASCII值大小逐个进行比较,比较的结果是一个数值向量,向量中的元素要么是1,要么是0。

  1. >> 'www0'>'W123'
  2. ans =
  3. 1×4 logical array
  4. 1 1 1 0

字符串比较函数用于判断字符串是否相等,有4种比较方式,函数如下:

  1. strcmp(s1,s2) :用来比较字符串 s1s2 是否相等,如果相等,返回结果为1,否则返回0。
  2. strncmp(s1,s2,n) :用来比较两个字符串前 n 个字符是否相等,如果相等,返回1,否则返回0。
  3. strcmpi(s1,s2) :在忽略字母大小写前提下,比较字符串 s1s2 是否相等,如果相等,返回1,否则返回0。
  4. strncmpi(s1,s2,n) :在忽略字母大小写前提下,比较两个字符串前 n 个字符是否相等,如果相等,返回1,否则返回0。
  1. >> strcmp('www0','W123')
  2. ans =
  3. logical
  4. 0
  5. >> strncmpi('www0','W123',1)
  6. ans =
  7. logical
  8. 1

字符串的查找与替换

  1. findstr(s1,s2) :返回短字符串在长字符串中的开始位置。
  2. strrep(s1,s2,s3) :将字符串 s1 中的所有子字符串 s2 替换为字符串 s3