《第3章程序设计.ppt》由会员分享,可在线阅读,更多相关《第3章程序设计.ppt(69页珍藏版)》请在三一办公上搜索。
1、第3章 MATLAB程序设计,M文件的概念与基本操作 MATLAB程序控制结构 MATLAB函数文件 MATLAB程序调试,3.1 M文件,3.1.1 M文件的分类 用MATLAB语言编写的程序,称为M文件。M文件可以根据调用方式的不同分为两类:(1)命令文件:Script File,也称为脚本文件;(2)函数文件:Function File。函数文件不能被执行,只能被调用,而脚本文件即可以被执行,也可以被调用。,例3-1 分别建立命令文件和函数文件,将华氏温度f转换为摄氏温度c。(1)建立命令文件并以文件名f2c.m存盘。clear,clc;%清除工作空间中的变量f=input(华氏温度f=
2、?);c=5*(f-32)/9然后在MATLAB的命令窗口中输入f2c,执行情况为:f2c华氏温度f=?73c=22.7778,(2)建立函数文件f2c1.m。function c=f2c1(f)c=5*(f-32)/9;然后在MATLAB的命令窗口调用该函数文件:clear,clcc=f2c1(73)c=22.7778f=input(华氏温度f=?);c=f2c1(f)华氏温度f=?73c=22.7778,3.1.2 M文件的建立与打开1建立新的M文件 有3种方法:(1)菜单操作 从File菜单中选择New,再选择M-file。(2)命令操作 在MATLAB命令窗口输入命令 edit(3)命
3、令按钮操作 单击New M-File命令按钮,2打开已有的M文件 也有3种方法:(1)菜单操作 从MATLAB主窗口的File菜单中选择Open。(2)命令操作 在MATLAB命令窗口输入命令:edit 文件名(3)命令按钮操作 单击Open File命令按钮。,3.2 程序控制结构3.2.1 顺序结构1数据的输出 MATLAB提供的命令窗口输出函数主要有disp函数,其调用格式为:disp(输出项)其中输出项既可以为表达式或字符串。DISP(X)displays the array,without printing the array name.a=1;disp(a)1,3.2 程序控制结构
4、3.2.1 顺序结构2数据的输入 从键盘输入数据,则可以使用input函数来进行,该函数的调用格式为:A=input(提示信息)或 A=input(提示信息,s)采用s选项,则不能输入定界符;否则必须输入。xm=input(Whats your name?,s);disp(My name is,xm,.)Whats your name?wang fangMy name is wang fang.,例3-2 输入x,y的值,并将它们的值互换后输出。程序如下:x=input(x=?);y=input(y=?);z=x;x=y;y=z;disp(x),disp(y)disp(x=,num2str(x
5、);y=,num2str(y),3程序执行的暂停 可以使用pause函数,其调用格式为:pause(延迟秒数)或 pause 直接使用pause,则将暂停程序,直到用户按任一键后程序继续执行。若要强行中止程序的运行可使用Ctrl+C命令。disp(Press any key to continue!),pausePress any key to continue!,例3-3 编写倒计时程序 程序如下:clear,clcinput(Press any key to start!),clc,disp(倒计时10秒:10)pause(1);clc,disp(倒计时10秒:9)pause(1);clc
6、,disp(倒计时10秒:8)pause(1);clc,disp(倒计时10秒:7)pause(1);clc,disp(倒计时10秒:6)pause(1);clc,disp(倒计时10秒:5)pause(1);clc,disp(倒计时10秒:4)pause(1);clc,disp(倒计时10秒:3)pause(1);clc,disp(倒计时10秒:2)pause(1);clc,disp(倒计时10秒:1)pause(1);clc,disp(倒计时10秒:0)load gong,sound(y,Fs)%锣声,例3-3 编写倒计时程序 程序如下:clear,clcinput(Press any k
7、ey to start!),clc,disp(倒计时10秒:10)for i=9:-1:0 pause(1);clc,disp(倒计时10秒:i)end%锣声load gong,sound(y,Fs)%鸟声 chirp%笑声 laughter%火车 train,3.2.2 选择结构1if语句(条件转移语句)if语句有3种格式:(1)单分支 ifend(2)双分支 ifelseend(3)多分支 ifelseif elseend,(1)单分支if语句:if 条件 语句组 end 当条件成立时,则执行语句组,执行完之后继续执行end后面的语句;若条件不成立,则直接执行end后面的语句。,(2)双分
8、支if语句:if 条件 语句组1 else 语句组2 end 当条件成立时,执行语句组1,否则执行语句组2,语句组1或语句组2执行后,再执行end后面的语句。,例3-4 写出下面“计算分段函数的值”程序的运行结果。x=input(请输入x的值:);if x=0 y=(x+sqrt(pi)/exp(2);exp(2)值为e2else y=log(x+sqrt(1+x*x)/2;endy程序执行结果:请输入x的值:5y=1.1562,(3)多分支if语句:if 条件1 语句组1 elseif 条件2 语句组2 elseif 条件m 语句组m else 语句组n end 注意:既使有多个条件同时成立
9、,只执行第1个满足条件的语句组。,例3-5 输入一个字符,若为大写字母,则输出其对应的小写字母;若为小写字母,则输出其对应的大写字母;若为数字字符则输出其对应的数值,若为其他字符则原样输出。c=input(请输入一个字符:,s);if c=A end,例3-6 某商场对顾客所购买的商品实行打折销售,标准如下(商品价格用price来表示):price200 没有折扣 200price500 3%折扣 500price1000 5%折扣 1000price2500 8%折扣 2500price5000 10%折扣 5000price 14%折扣输入所售商品的价格,求其实际销售价格。,程序1:pri
10、ce=input(请输入商品价格:);if price=200 endprice=price*(1-rate)%输出商品实际销售价格,程序2:price=input(请输入商品价格:);if price 200 rate=0;elseif price 500 rate=3/100;elseif price 1000 rate=5/100;elseif price 2500 rate=8/100;elseif price 5000 rate=10/100;else%价格大于等于5000 rate=14/100;endprice=price*(1-rate)%输出商品实际销售价格,2.switch
11、语句 switch语句根据表达式的取值不同,分别执行不同的语句,其语句格式为:switch 表达式 case 表达式1 语句组1 case 表达式m 语句组m otherwise 语句组n end 注意:既使有多个case表达式与switch表达式值相同,只执行其中的第1个case对应的语句组。,上例3-6price=input(请输入商品价格:);switch fix(price/100)case 0,1%价格小于200,构成cell数据 rate=0;case 2,3,4%价格大于等于200但小于500 rate=3/100;case num2cell(5:9)%价格大于等于500但小于1
12、000 rate=5/100;case num2cell(10:24)%价格大于等于1000但小于2500 rate=8/100;case num2cell(25:49)%价格大于等于2500但小于5000 rate=10/100;otherwise%价格大于等于5000 rate=14/100;endprice=price*(1-rate)%输出商品实际销售价格,3.2.3 循环结构1.for 语句 for语句的格式为:for 循环变量=行向量 循环体 end 执行过程是依次将各列元素赋给循环变量,然后执行循环体。常用冒号表达式产生行向量。表达式1:表达式2:表达式3。步长为1时,表达式2可
13、以省略。,例3-7 写出下列程序的执行结果。s=0;for k=1,5,4 s=s+k;end disp(s);结果:10,例3-8 一个三位整数各位数字的立方和等于该数本身则称该数为水仙花数。输出全部水仙花数。程序如下:for m=100:999 m1=fix(m/100);%求m的百位数字 m2=mod(fix(m/10),10);%求m的十位数字 m3=mod(m,10);%求m的个位数字 if m=m1*m1*m1+m2*m2*m2+m3*m3*m3 disp(m)endend,例3-9 已知 求y的值。程序如下:y=0;for n=1:100 y=y+1/(n*n);endy,2.w
14、hile语句 while语句的一般格式为:while(条件)循环体 end 其执行过程为:若条件成立,则执行循环体语,执行后再判断条件是否成立,如果不成立则跳出循环。,例3-10 从键盘输入若干个数,当输入0时结束输入,求这些数的平均值和它们之和。程序如下:sum=0;cnt=0;val=input(Enter a number(end in 0):);while(val=0)sum=sum+val;cnt=cnt+1;val=input(Enter a number(end in 0):);endif(cnt 0)sum mean=sum/cntend,3.2.2.3 break语句和con
15、tinue语句 与循环结构相关的语句还有break语句和continue语句。它们一般与if语句配合使用。break语句用于终止循环的执行。当在循环体内执行到该语句时,程序将跳出循环,继续执行循环语句的下一语句。continue语句控制跳过循环体中的某些语句。当在循环体内执行到该语句时,程序将跳过循环体中所有剩下的语句,继续下一次循环。提前折回!,例3-11 求100,200之间第一个能被21整除的整数。程序如下:for n=100:200 if mod(n,21)=0 continue end breakendn结果:n=105,3.2.2.4 循环的嵌套 如果一个循环结构的循环体又包括一个
16、循环结构,就称为循环的嵌套,或称为多重循环结构。for for end end,例3-12 若一个数等于它的各个真因子之和,则称该数为完数(完全数、完备数或完美数),如6=1+2+3,所以6是完数。求1,500之间的全部完数。程序如下:for m=1:500 s=0;for k=1:m/2 if mod(m,k)=0 s=s+k;end end if m=s disp(m);endend,3.3 函数文件 函数文件由function语句引导,其基本结构为:function 输出形参表=函数名(输入形参表)函数体 其中以function开头的一行为引导行,表示该M文件是一个函数文件。函数名的命名
17、规则与变量名相同。输入形参为函数的输入参数,输出形参为函数的输出参数。当输出形参多于一个时,则应该用方括号括起来。,例3-13 编写函数文件求半径为r的圆的面积和周长。函数文件csp.m 如下:function s,p=fcircle(r)%CIRCLE calculate the area and perimeter of a circle of radii r%r-圆半径,s-圆面积,p-圆周长 s=pi*r*r;p=2*pi*r;s,p=csp(10)s=314.1593 p=62.8319,3.3.2 函数调用 函数调用的一般格式是:输出实参表=函数名(输入实参表)要注意的是,函数调用
18、时各实参出现的顺序、个数,应与函数定义时形参的顺序、个数一致,否则会出错。函数调用时,先将实参传递给相应的形参,从而实现参数传递,然后再执行函数的功能。在MATLAB中,函数可以嵌套调用,即一个函数可以调用别的函数,甚至调用它自身。一个函数调用它自身称为函数的递归调用。,例3-14 利用函数的递归调用,求n!。递归调用函数文件factor.m如下:function f=factor(n)if n=1 f=1;else f=factor(n-1)*n;%递归调用求(n-1)!end,3.3.3 函数参数的可调性 在调用函数时,MATLAB用两个永久变量nargin和nargout分别记录调用该函
19、数时的输入实参和输出实参的个数。只要在函数文件中包含这两个变量,就可以准确地知道该函数文件被调用时的输入输出参数个数,从而决定函数如何进行处理。,例3-15 建立函数文件sum1.m,实现sum函数功能。程序1:function s=sum1(x,dim)row,col=size(x);if dim=1 for i=1:col s(i)=0;for j=1:row s(i)=s(i)+x(j,i);end endelse for i=1:row s(i)=0;for j=1:col s(i)=s(i)+x(i,j);end s=s;endend,例3-16 建立函数文件sum1.m,实现sum
20、函数功能。程序2:function s=sum1(x,dim)row,col=size(x);if nargin=1|dim=1 for i=1:col s(i)=0;for j=1:row s(i)=s(i)+x(j,i);end endelse for i=1:row s(i)=0;for j=1:col s(i)=s(i)+x(i,j);end s=s;endend,3.4 程序调试3.4.1 程序调试概述 一般来说,应用程序的错误有两类,一类是语法错误,另一类是运行时的错误。语法错误包括词法或文法的错误,例如函数名的拼写错、表达式书写错等。程序运行时的错误是指程序的运行结果有错误,这类
21、错误也称为程序逻辑错误。,3.4.2 调试菜单,1断点操作 F12 F5K F12 F5,3.5.2 调试菜单,2控制单步运行 F10,3.6 编程技巧,1.矢量化 用矢量或矩阵取代循环语句。tic%Start a stopwatch timer s=0;for i=1:5000 s=s+i;y(i)=i*2;end s,y toc%Read the stopwatch timer可改为:tic i=1:5000;s=sum(i);y=i*2;s,y toc,例3-9中程序y=0;for n=1:100 y=y+1/(n*n);endy 通常由下面的程序来代替:n=1:100;y=sum(1.
22、/(n.*n);y,2.预分配内存空间 预分配矢量或矩阵的内存空间。tic for i=1:1000 y(i)=i*2;end y toc可改为:tic y=zeros(1,100);for i=1:100 y(i)=i*2;end y toc,程序设计举例,例1任意输入三个数,求最大值和最小值edit li1_1a=input(a=?);b=input(b=?);c=input(c=?);max=-99999;min=99999;if maxa max=a;endif maxb max=b;endif maxc max=c;end,if mina min=a;endif minb min=b
23、;endif minc min=c;endminmax,edit li1_2a=input(a=?);b=input(b=?);c=input(c=?);max=a;min=a;if maxb min=b;endif minc min=c;endmin,max,edit li1_3a=input(a=?);b=input(b=?);c=input(c=?);if ab x=a;a=b;b=x;endif bc x=b;b=c;c=x;endif ab x=a;a=b;b=x;endfprintf(min=%d,max=%dn,a,c),edit li1_4 a=input(a=?);b=inp
24、ut(b=?);c=input(c=?);abc0=a,b,cabc=sort(abc0);%默认为 ascend升序sort(abc0,2,descend)%为降序排列 max=abc(3),min=abc(1),例2 已知 求y的值。edit li2_1y=0;for n=1:100 y=y+1/n;endy 在实际编程中,采用循环语句会降低其执行速度,所以前面的程序通常由下面的程序来代替:edit li2_2n=1:100;y=sum(1./n);y,例3求自然数1100中的奇数和。edit li3_1 s=0;for i=1:100 if mod(i,2)=0 s=s+i;endend
25、fprintf(sum=%d n,s),edit li3_2 s=0;for i=1:2:100 s=s+i;endfprintf(sum=%d n,s),edit li3_3s=sum(1:2:100);fprintf(sum=%d n,s),例4求自然数1100中的奇数和及偶数和。edit li4_1 sj=0;so=0;for i=1:100 if mod(i,2)=0 so=so+i;else sj=sj+i;endendfprintf(sumj=%d,sumo=%d n,sj,so),edit li4_2sj=sum(1:2:100);so=sum(2:2:100);fprintf(
26、sumj=%d,sumo=%d n,sj,so),例5一个数是7的倍数,且除以26时均余1。edit li5_1clear,clcfor x=7:7:1000 if mod(x,2)=1&mod(x,3)=1&mod(x,4)=1&mod(x,5)=1&mod(x,6)=1 disp(x)break endend,edit li5_2clear,clcclear,clcx=7;while mod(x,2)=1|mod(x,3)=1|mod(x,4)=1|mod(x,5)=1|mod(x,6)=1 x=x+7;endx,edit li5_3for x=6:6:2*3*4*5*6 if mod(x
27、,2)=0&mod(x,3)=0&mod(x,4)=0&mod(x,5)=0 break endendfor y=(x:x:1000)+1 if mod(y,7)=0 break endendy,edit li5_4x=6;while mod(x,2)=0|mod(x,3)=0|mod(x,4)=0|mod(x,5)=0 x=x+6;endy=x;while mod(y+1,7)=0 y=y+x;endy+1,例6任意输入十个自然数,求其最大公约数。edit li6_1clear,clcfor i=1:10 x(i)=input(x=?);endminx=min(x);for j=minx:-
28、1:1 if sum(mod(x,j)=0 break endendj,例6任意输入十个自然数,求其最大公约数。edit li6_2clear,clcfor i=1:10 fprintf(x(%d)=?,i),x(i)=input();endminx=min(x);for j=minx:-1:1 if sum(mod(x,j)=0 break endendj,例7一个三位整数各位数字的立方和等于该数本身则称该数为水仙花数。输出全部水仙花数。edit li7_1 for m=100:999 m1=fix(m/100);%求m的百位数字 m2=mod(fix(m/10),10);%求m的十位数字
29、m3=mod(m,10);%求m的个位数字 if m=m1*m1*m1+m2*m2*m2+m3*m3*m3 disp(m)endend,例8求100,200之间第一个能被21整除的整数。edit li8_1 for n=100:200 if mod(n,21)=0 break end endn,例8求100,200之间第一个能被21整除的整数。edit li8_2 for n=100:200 if mod(n,21)=0 continue end breakendn,例8求100,200之间第一个能被21整除的整数。edit li8_3 clear,clcx=21;while x100 x=x+21;endx,例9若一个数等于它的各个真因子之和,则称其为完数,如6=1+2+3,所以6是完数。求1,500之间的全部完数。edit li9_1for m=1:500 s=0;for k=1:m/2 if mod(m,k)=0 s=s+k;end end if m=s disp(m);endend,