1、 Basic Matrix Operations一、实验目的1、 掌握向量和矩阵的创建方法;2、 掌握向量和矩阵元素的索引方法;3、 掌握向量和矩阵的基本操作;4、 利用 MATLAB编写程序进行矩阵运算。二、基础知识 1、常见数学函数函 数 名 数 学 计 算 功 能 函 数 名 数 学 计 算 功 能Abs(x) 实数的绝对值或复数的幅值 floor(x) 对x朝-方向取整 Acos(x) 反余弦arcsin x gcd(m,n) 求正整数m和n的最大公约数 acosh(x) 反双曲余弦arccosh x imag(x) 求复数x的虚部 angle(x) 在四象限内求复数 x 的相角 lc
2、m(m,n) 求正整数m和n的最小公倍数 asin(x) 反正弦arcsin x log(x) 自然对数(以 e为底数) asinh(x) 反双曲正弦arcsinh x log10(x) 常用对数(以10为底数) atan(x) 反正切arctan x real(x) 求复数x的实部 atan2(x,y) 在四象限内求反正切 Rem(m,n) 求正整数m和n的m/n之余数 atanh(x) 反双曲正切arctanh x round(x) 对x四舍五入到最接近的整数 ceil(x) 对x朝+方向取整 sign(x) 符号函数:求出x的符号 conj(x) 求复数x的共轭复数 sin(x) 正弦s
3、in x cos(x) 余弦cos x sinh(x) 反双曲正弦sinh x cosh(x) 双曲余弦cosh x sqrt(x) 求实数x的平方根: x exp(x) 指数函数 xe tan(x) 正切tan x fix(x) 对x朝原点方向取整 tanh(x) 双曲正切tanh x 2、常量与变量 系统的变量命名规则:变量名区分字母大小写;变量名必须以字母打头,其后可以是任意字母,数字,或下划线的组合。此外,系统内部预先定义了几个有特殊意义和用途的变量,见下表: 特殊的变量、常量 取 值ans 用于结果的缺省变量名 pi 圆周率的近似值(3.1416) eps 数学中无穷小(epsilo
4、n)的近似值(2.2204e - 016) inf 无穷大,如 1/0 = inf (infinity) NaN 非数,如 0/0 = NaN (Not a Number),inf / inf = NaN i,j 虚数单位:i = j =1 数值型向量(矩阵)的输入 任何矩阵(向量),可以直接按行方式输入每个元素:同一行中的元素用逗号(,)或者用空格符来分隔;行与行之间用分号(;)分隔。所有元素处于一方括号( )内; 例1: Time = 11 12 1 2 3 4 5 6 7 8 9 10 X_Data = 2.32 3.43;4.37 5.98 系统中提供了多个命令用于输入特殊的矩阵: 函
5、数 功 能 函数 功 能 compan 伴随阵 toeplitz Toeplitz矩阵 diag 对角阵 vander Vandermonde矩阵 hadamard Hadamard矩阵 zeros 元素全为0的矩阵 hankel Hankel矩阵 ones 元素全为1的矩阵 invhilb Hilbert矩阵的逆阵 rand 元素服从均匀分布的随机矩阵 kron Kronercker张量积 randn 元素服从正态分布的随机矩阵 magic 魔方矩阵 eye 对角线上元素为1的矩阵 pascal Pascal矩阵 meshgrid 由两个向量生成的矩阵 上面函数的具体用法,可以用帮助命令he
6、lp得到。如:meshgrid(x,y) 输入 x=1 2 3 4; y=1 0 5; X,Y=meshgrid(x, y),则 X = Y = 1 2 3 4 1 1 1 1 1 2 3 4 0 0 0 0 1 2 3 4 5 5 5 5 目的是将原始数据x,y转化为矩阵数据X,Y。 3、数组(矩阵)的点运算 运算符:+(加)、-(减)、./(右除)、.(左除)、.(乘方), 例3: g = 1 2 3 4;h = 4 3 2 1; s1 = g + h, s2 = g.*h, s3 = g.h, s4 = g.2, s5 = 2.h 4、矩阵的运算 运算符:+(加)、-(减)、*(乘)、/
7、(右除)、(左除)、(乘方)、(转置)等; 常用函数:det(行列式)、inv(逆矩阵)、rank(秩)、eig(特征值、特征向量)、rref(化矩阵为行最简形) 例4: A= 2 0 1; 1 3 2; B= 1 7 1; 4 2 3; 2 0 1; M = A*B % 矩阵A与B按矩阵运算相乘 M =0 14 -317 13 10 det_B = det(B) % 矩阵A的行列式 det_B =20 rank_A = rank(A) % 矩阵A的秩 rank_A =2 inv_B = inv(B) % 矩阵B的逆矩阵 inv_B =0.1000 -0.3500 1.15000.1000 0
8、.1500 -0.3500-0.2000 0.7000 -1.3000 V,D = eig(B) % 矩阵B的特征值矩阵V与特征向量构成的矩阵D =7.2680 0 0 0 -1.6340 + 0.2861i 0 0 0 -1.6340 - 0.2861i X = A/B % A/B = A*B-1,即XB=A,求X 0.4000 -1.4000 3.60000.0000 1.5000 -2.5000 Y = BA % BA = B-1*A,即BY=A,求Y 三、实验内容1、练习数据和符号的输入方式,将前面的命令在命令窗口中执行通过。 2、键入常数矩阵输入命令: a = 1 2 3 与 a =
9、 1;2;3 记录结果,比较显示结果有何不同;b = 1 2 5 与 b = 1 2 5; 记录结果,比较显示结果有何不同; a a b b 记录结果,比较变量加“”后的区别; c = a * b 1 2 52 4 103 6 15 c = a* b 记录显示结果与出错原因; a = 1 2 3; 4 5 6; 7 8 0,求a2 a0.5 。30 36 1566 81 4239 54 690.5977 + 0.7678i 0.7519 + 0.0979i 0.5200 - 0.4680i1.4102 + 0.1013i 1.7741 + 0.6326i 1.2271 - 0.7467i1.2
10、757 - 1.0289i 1.6049 - 1.0272i 1.1100 + 1.6175i3、使用冒号选出指定元素:已知 A=1 2 3;4 5 6;7 8 9,求 A 中第 3 列前 2 个元素,A 中所有列第 2,3 行的元素。ns =36ns =4 5 67 8 04、输入 A=7 1 5; 2 5 6; 3 1 5,B=1 1 1; 2 2 2; 3 3 3,在命令窗口中执行下列表达式,掌握其含义: A(2,3)ans =6 A(:,2)A(3,:) A(:,1:2:3) ans =7 52 63 5 A(:,3).*B(:,2) ns =51215A(:,3)*B(2,:) A*
11、B A.*B A2 A.2 B/A B./A 5、建立 M 文件,求 的逆矩阵。nv_M =1234A1.0000 3.0000 -2.0000-1.5000 -3.0000 2.50001.0000 1.0000 -1.00006、 设 , , ,建立 M 文件,求矩阵 X ,使1234A15B320C满足:AXB = C 。四,详细设计(1)存储要点positioncol=positioncol-1+numcol-1;三元组表(row,col,v)稀疏矩阵(行数 m,列数 n,非零元素个数 t) ,三元组,.,三元组)row col vA-data0 0 4 81 1 0 12 1 2 3
12、3 2 1 24 3 0 6 max-1 (2)乘法运算要点已知稀疏矩阵 A(m1 n1)和 B(m2 n2),求乘积 C(m1 n2)。稀疏矩阵 A、B、C 及它们对应的三元组表 A.data、B.data 、C.data 如图 6 所示。由矩阵乘法规则知:C(i,j)=A(i,1)B(1,j)+A(i,2)B(2,j)+A(i,n)B(n,j)=这就是说只有 A(i,k)与 B(k,p)(即 A 元素的列与 B 元素的行相等的两项)才有相乘的机会,且当两项都不为零时,乘积中的这一项才不为零。矩阵用二维数组表示时,a11 只有可能和 B 中第 1 行的非零元素相乘,a12 只有可能和 B 中
13、第 2 行的非零元素相乘,而同一行的非零元是相邻存放的,所以求 c11 和 c12 同时进行:求 a11*b11 累加到c11,求 a11*b12 累加到 c12,再求 a12*b21 累加到 c11,再求 a12*b22 累加到 c22.,当然只有 aik 和bkj(列号与行号相等)且均不为零(三元组存在)时才相乘,并且累加到 cij 当中去。(3)稀疏矩阵的快速转置要点:矩阵 A 中三元组的存放顺序是先行后列,对同一行来说,必定先遇到列号小的元素,这样只需扫描一遍 A.data 。所以需引入两个向量来实现 :numn+1和 position n+1,numcol表示矩阵 A 中第 col
14、列的非零元素的个数 (为了方便均从 1 单元用起),position col初始值表示矩阵 A 中的第 col 列的第一个非零元素在 B.data 中的位置。于是 position 的初始值为:position 1=1;position col= position col-1+numcol-1; 2coln依次扫描 A.data,当扫描到一个 col 列元素时,直接将其存放在 B.data 的 position col位置上,position col加 1,position col中始终是下一个 col 列元素在 B.data 中的位置。A-row0 01 12 33 4(4)逆矩阵判断矩阵是
15、否为方阵逆矩阵的算法:求行列式的值求矩阵的伴随矩阵用伴随矩阵除以行列式 求逆矩阵的流程:五、源程序(测试结果)#include#include#include#includeusing namespace std;#define max 100#define datatype int typedef structint row,col;/行,列datatype v;/非 0数值Node;typedef structNode datamax;/稀疏矩阵int m,n,t;/m行,n 列,t 非 0数个数Matrix;/*求逆矩阵存储*/typedef struct /存储结构int m, n;
16、/行、列数double *p; /矩阵基址nMatrix;void In(nMatrix a) /求逆输入 couta.ma.n;int m = a.m, n = a.n;int i, j;double *p = a.p = new doublem * n; /p是行指针coutpj; /即 a.pi*n+jvoid Out(nMatrix a) /求逆输出 int m = a.m, n = a.n;int i, j;double *p = a.p;for (i = 0; i (istreamcoutA.m;coutA.n;coutA.t;for(i=1;iA.datai.rowA.datai
17、.colA.datai.v;return input;ostreamj+;k+;elseif(A.datai.colB.dataj.col)C.datak=B.dataj;j+;k+;elseif(A.datai.v+B.dataj.v!=0)C.datak.row=A.datai.row;C.datak.col=A.datai.col;C.datak.v=A.datai.v+B.dataj.v;k+;i+;j+; while(iB.dataj.row) C.datak=B.dataj;j+;k+;else if(A.datai.colB.dataj.col) C.datak=B.dataj;
18、j+;k+;else if(A.datai.v-B.dataj.v!=0) C.datak.row=A.datai.row;C.datak.col=A.datai.col;C.datak.v=A.datai.v-B.dataj.v;k+;i+;j+; while(iA; coutB; cout“b=n“B;C=A+B;cout“a+b=n“C;C=A-B;cout“a-b=n“C;C=A*B;cout“a*b=n“C;C=A;cout“a=n“C;In(a);cout“矩阵的行列式为:“endl;coutDet(a)endl;cout“矩阵的逆为:“endl;temp=!a;cout“!a=n
19、“Trsendl;六、总结这次数据结构课程设计的制作使我对 matlab的理解更加深刻,也使我认识到了自己很多不足之处。我发现自己在处理稍微具体的程序时显得无从下手,以前学习的知识只是理论性的知识,并没有真正实践过,当我通过网上查询、请教同学、复习知识后才对编写程序有了初步的思路。后来编写程序时也碰到了许多错误,我对于指针的掌握程度较差导致了我在使用的时候产生了很多错误,请教了学习较好的同学后才逐步完成。最后还有很多细节方面难以修改,于是就改进算法,使自己的程序有了雏形。这次程序设计使我认识到,要做成编写一个完整的程序绝对不是一件简单的事情,不单要掌握基础知识更要勇于实践,不单要舍得花费时间更要用心去完成它。无论是编写程序还是完成现实生活中的其他事情,我们都必须按部就班地从点滴做起,逐步完成。不但要完成更要做到尽善尽美。学习数据结构的历程不会因为完成本次课程设计而停止,我是为了用知识武装大脑而学习,通过学习充实自己的生活,我一定会努力学习,争取以后能够完成规模更大的程序。