字符与字符串、元胞、结构体、函数、符号运算、数据处理
字符与字符串
字符数组用单引号, 字符串用双引号.
strlength
可以求出字符串的长度.
通过 char
可以将字符串转化为字符数组; 相应的, 可以用 string
将字符数组转化为字符串.
字符串在数组中的地位与字符数组地位不同, 字符数组为多个值, 字符串为一个值, 可以看作是叠在二维上但保持数组本身维度不变的字符数组整体.
字符串占据了第二维, 因此字符串行向量是排在第三维上的:
% 2x3 -> 2x2x3
>> char(["s1", "s2", "s3"; "s4", "s5", "s6"])
(:, :, 1) = ['s1'; 's4']
(:, :, 2) = ['s2'; 's5']
(:, :, 3) = ['s3'; 's6']
% 2x3 -> 2x1
>> string(['1', '2', '3'; '4', '5', '6'])
["123"; "456"]
字符串作为一个整体值, 无法像字符数组一样支持ASCII值运算如减法、加法之类的.
字符串的加法为连接字符串.
字符数组与字符串可以和数字相互转化.
当使用 double
进行转化时, 字符数组是将ASCII值转化为 double
类型; 而字符串则会“忠实地”将字面值数字 (包括中间带一个空格、逗号或单撇的数字) 转化出来.
str2double
和 str2num
可以对字符数组和字符串作用, 按字符字面提取数字:
>> double(['123'; '1e2'])
[49, 50, 51; 49, 101, 50]
>> double(["123"; "1e2"])
[123.0000; 100.0000]
>> double(["123", "456"])
[123, 456]
>> double(["123 456", "123,456", "123'456"])
[123456, 123456, 123456]
>> str2double(['123', '1e5'])
123100000
>> str2double(['123'; '456']) % 对于非向量字符数组, 按照迭代顺序提取
142536
>> str2double(['123'; '4e6']) % 同上
1.4200e+38
>> str2double(["123", "456"])
[123, 456]
>> str2double(["123,456"; "123 456"; "123'456"]) % 只有逗号分割被允许
[123456; NaN; NaN]
% str2num类似于Python里的eval
>> str2num('123; 456')
[123; 456]
>> str2num("123; 456")
[123; 456]
string
可以直接将数字转为一个字符串; 而想要变成字符数组, 需要使用 num2str
.
>> num2str([123, 456])
'123 456'
字符数组可以索引, 字符串为整体值, 没有内部索引.
元胞
元胞类似于表格, 可以自动扩充.
当我们用小括号索引 (也就是通常的索引时), 我们总是得到一个元胞; 而当我们使用大括号索引时, 我们才能取到元胞中的值.
与数组不同, 元胞允许空值的存在, 我们没有赋值的地方默认为 []
.
对一个元胞赋值为 []
时可以清除这个元胞; 但是对元胞内容赋值为 []
只能清除内容.
>> a = {1, 2, 3};
>> a{2, 2} = 'a'
{1, 2, 3;
[], 'a', []}
>> a(3, 3) = {1>0}
{1, 2, 3;
[], 'a', [];
[], [], 1}
>> for i = 1:3
a{i, i} = []; % 对元胞内部赋空值
end
>> a
{[], 2, 3;
[], [], [];
[], [], []}
>> for i = 1:3
a(1, :) = []; % 清除元胞
end
>> a
0x3 cell
元胞在数组中具有主导地位, 可以自动吸纳非元胞数据, 除非外面还有一层元胞:
>> [{1, 2}, 3]
{1, 2, 3}
>> {{1, 2}, 3}
{1x2 cell, 3}
mat2cell
和 cell2mat
使得我们可以进行类似分块矩阵的运算:
>> a = [1, 2, 3, 4;
5, 6, 7, 8;
9, 10, 11, 12];
>> mat2cell(a, [1, 2], [1, 3])
{1, [2, 3, 4];
[5, 9], [6, 7, 8; 10, 11, 12]}
>> cell2mat({[1, 2], 3; [4, 5], 6})
[1, 2, 3; 4, 5, 6]
结构体
结构体类似于数据库, 对于其中每一组数据 (用索引取得), 分为若干字段记录数据.
>> s1.a = 1; s1.b = 'q'
s1 =
a | b
1 | 'q'
>> s1(2).a = 2; s1(2).b = 'w'
s1 =
a | b
1 | 'q'
2 | 'w'
>> s2 = struct('a', {1, 2}, 'b', {'q'})
s2 =
a | b
1 | 'q'
2 | 'q'
>> s2 = struct('a', {{1, 2}}, 'b', {'q'})
s2 =
a | b
1x2 cell | 'q'
结构体一次读取多个数据时, 会逐个将其输出而不是放入一个数组或元胞, 因此如果需要转运这些数据, 需要外面包裹数组或元胞:
>> a = struct('a', {78, 'char'});
>> [a.a]
'Nchar'
>> {a.a}
{78, 'char'}
结构体实际上是一种数组, 可以像常规数组一样合并.
其中, 2x1结构体和1x2结构体是类似的, 但是合并时就会变成二维结构体数组:
>> s1.x = 1; s1.y = 1;
>> s2.x = 2; s2.y = 2;
>> s3.x = 3; s3.y = 3;
>> s4.x = 4; s4.y = 4;
>> s = [s1, s2; s3, s4]
2x2 struct
>> s(1, 1)
x | y
1 | 1
函数
输入 [x1, ...]
输出 [y1, ...]
的函数 func
定义为:
function [y1, ...] = func(x1, ...)
cmd
end
MATLAB定义函数一般从文件下方开始往上定义, 对于函数文件, 主函数须放在开头, 并且与文件名同; 而脚本中的局部函数, 只能放在文件最末尾.
句柄, 负责将函数进行传递以实现复杂功能的数据类型. 通过 @
即可得到函数的句柄, 包括匿名函数:
>> a = 1;
>> f = @(x, y) a*x.*y;
>> clear a; % 与Python不同, 定义匿名函数时, a的值已经被记录为常值了
>> f([1, 2, 3], [4, 5, 6])
[4, 10, 18]
符号运算
定义变量:
syms a b % 定义变量
syms c [2, 3] % 定义矩阵
syms 'd%d%d' [2, 3] % 对元素命名格式化
syms e 2 % 定义方阵
工作区:
a: 1x1 sym
b: 1x1 sym
c: 1x1 sym
c1_1 c1_2 c1_3 c2_1 c2_2 c2_3: 1x1 sym
d: 1x1 sym
d11 d12 d13 d21 d22 d23: 1x1 sym
e: 1x1 sym
e1_1 e1_2 e2_2 e_2: 1x1 sym
定义函数:
syms f(x) g(y)
工作区:
f: 1x1 symfun
g: 1x1 symfun
x: 1x1 sym
也可以使用 sym
函数式定义, 这时, 我们可以直接定义一个矩阵而非像 syms
一样用元素挤占工作区:
>> a = sym('a', 2)
a =
a_1,1 a_1,2
a_2,1 a_2,2
>> b = sym('b_q%d_%d', 2)
b =
b_q1,1 b_q1,2
b_q2,1 b_q2,2
% 以上输出的下划线指后面为脚标
有了这些变量的定义, 我们可以像正常数值一样计算它们, 但是符号计算是精确的:
>> 1/sym(123456)
1/123456
>> sym(1/123456)
1195356666259043/147573952589676412928
对于符号函数, 我们可以直接像常规函数一样使用; 但是对于符号运算出来的式子, 应当使用 subs
来进行数值计算:
>> syms a b
>> c = a+b^2;
>> subs(c, [a, b], [1.5, 1])
5/2
>> subs(c, {a, b}, {[1.5, 1; 2.1, 2], [1, 1; 3.25, 4]})
[5/2, 2; 1013/80, 18]
数据处理
前面的 save
和 load
分别有自己的函数式.
除了这两个, 还有读取文本的 fileread
、向文本写入表格的 writetable
、读取表格的 readtable
、读取图像的 imread
和写图像的 imwrite
.
曲线拟合器
在APP中选择曲线拟合器, 选择数据和拟合模型后, 即可得到拟合结果.
其中, 线性拟合为选择基函数, 通过基函数的线性组合进行拟合.
直方图
使用 histogram(data)
绘制 data
的直方图.
可以指定为 histogram(data, n)
或者 histogram(data, arr)
来确定其直方图的分组数, 其中 n
直接指定分组数, arr
指定分割点 (左闭右开).
histogram(..., key, value)
可以指定图的相关属性:
histogram(data, 'Normalization', 'probability') % 矩形高度表示频率
histogram(data, 'Normalization', 'pdf') % 矩形面积表示频率
histogram(data, 'FaceColor', [0.9,0.5,0.2]) % 调整颜色
零星补充:
[a, b] = deal([1, 2]) % 用deal实现解包
a = 1 b = 2
integral(@(x) x.^2, 0, 1) % 数值积分
0.3333
syms f(x)
f(x) = x.^2;
diff(f, 2) % f的二阶导
2
fourier(cos(x)) % Fourier变换
pi*(dirac(w-1)+dirac(w+1))
laplace(f) % Laplace变换
2/s^3