QQ登录

只需要一步,快速开始

 注册地址  找回密码
查看: 17153|回复: 7
打印 上一主题 下一主题

maple基础

[复制链接]
字体大小: 正常 放大

1

主题

5

听众

4

积分

升级  80%

该用户从未签到

自我介绍
爱学习
跳转到指定楼层
1#
发表于 2012-6-12 16:53 |只看该作者 |倒序浏览
|招呼Ta 关注Ta
% v) p# E9 @4 l7 z* Y' n
第一章  Maple基础4 J# A) z3 S" e# t% p, w0 v
' i  L9 @7 J, b$ E6 z  ^) H
1 初识计算机代数系统Maple
: r$ T- f. Q4 y4 z; J0 }2 `1 X+ c, P1.1 Maple简说% E" w; D; }1 a5 R) E
1980年9月, 加拿大Waterloo大学的符号计算机研究小组成立, 开始了符号计算在计算机上实现的研究项目, 数学软件Maple是这个项目的产品. 目前, 这仍是一个正在研究的项目.
( \! `0 X, f$ ]Maple的第一个商业版本是1985年出版的. 随后几经更新, 到1992年, Windows系统下的Maple 2面世后, Maple被广泛地使用, 得到越来越多的用户. 特别是1994年, Maple 3出版后, 兴起了Maple热. 1996年初, Maple 4问世, 1998年初, Maple 5正式发行. 目前广泛流行的是Maple 7以及2002年5月面市的Maple 8.
+ r% H2 [* A4 N  gMaple是一个具有强大符号运算能力、数值计算能力、图形处理能力的交互式计算机代数系统(Computer Algebra System). 它可以借助键盘和显示器代替原来的笔和纸进行各种科学计算、数学推理、猜想的证明以及智能化文字处理.
9 G) j: w6 L! y' v! x* DMaple这个超强数学工具不仅适合数学家、物理学家、工程师, 还适合化学家、生物学家和社会学家, 总之, 它适合于所有需要科学计算的人.
% A& p6 E3 s6 g3 U* ?1.2 Maple结构
$ l% \1 l" C5 y6 v0 |! v& sMaple软件主要由三个部分组成: 用户界面(Iris)、代数运算器(Kernel)、外部函数库(External library). 用户界面和代数运算器是用C语言写成的, 只占整个软件的一小部分, 当系统启动时, 即被装入, 主要负责输入命令和算式的初步处理、显示结果、函数图象的显示等. 代数运算器负责输入的编译、基本的代数运算(如有理数运算、初等代数运算等)以及内存的管理. Maple的大部分数学函数和过程是用Maple自身的语言写成的, 存于外部函数库中. 当一个函数被调用时, 在多数情况下, Maple会自动将该函数的过程调入内存, 一些不常用的函数才需要用户自己调入, 如线性代数包、统计包等, 这使得Maple在资源的利用上具有很大的优势, 只有最有用的东西才留驻内存, 这保证了Maple可以在较小内存的计算机上正常运行. 用户可以查看Maple的非内存函数的源程序, 也可以将自己编的函数、过程加到Maple的程序库中, 或建立自己的函数库. & Q* z9 e" w; n
1.3 Maple输入输出方式8 M  R: z# B: @
为了满足不同用户的需要, Maple可以更换输入输出格式: 从菜单“Options | Input Display和Out Display下可以选择所需的输入输出格式. 3 J; L* P( H. }# s* P
Maple 7有2种输入方式: Maple语言(Maple Notation)和标准数学记法(Standard Math Notation). Maple语言是一种结构良好、方便实用的内建高级语言, 它的语法和Pascal或C有一定程度的相似, 但有很大差别. 它支持多种数据操作命令, 如函数、序列、集合、列表、数组、表, 还包含许多数据操作命令, 如类型检验、选择、组合等. 标准数学记法就是我们常用的数学语言.
" t+ O6 I7 t" ?2 M启动Maple, 会出现新建文档中的“[>”提示符, 这是Maple中可执行块的标志, 在“>”后即可输入命令, 结束用“;”(显示输出结果)或者“:”(不显示输出结果). 但是, 值得注意的是, 并不是说Maple的每一行只能执行一句命令, 而是在一个完整的可执行块中健入回车之后, Maple会执行当前执行块中所有命令(可以是若干条命令或者是一段程序). 如果要输入的命令很长, 不能在一行输完, 可以换行输入, 此时换行命令用“shift+Enter”组合键, 而在最后一行加入结束标志“;”或“:”, 也可在非末行尾加符号“\”完成.
) c/ R" f' O% D, CMaple 7有4种输出方式: Maple语言、格式化文本(Character Notation)、固定格式记法(Typeset Notation)、标准数学记法(Standard Math Notation). 通常采用标准数学记法. 5 K* R4 K% V; q( ~! P5 n+ X' I. f
Maple会认识一些输入的变量名称, 如希腊字母等. 为了使用方便, 现将希腊字母表罗列如下,输入时只需录入相应的英文,要输入大写希腊字母, 只需把英文首字母大写:   
. T! k8 w0 H. _
* Y; b$ z6 c9 i
7 s( L! \4 y# F; c . }) L. I% M& K( N
7 K$ l4 U! S' s5 B: D
8 t5 {2 S/ e7 Y# U, b

! F2 N) x9 Z* X. S( H
3 g5 i) C) T' m: _! C* Q ( n; f  [( c; |4 v9 R/ \% A
) X; H/ O; ]2 X% c( |! ~. k

! u: [$ f: N9 j2 I# `) M
2 P8 N, v! |, w* Z3 P
! D+ c' d) S" Q( \7 j+ j. P8 K5 b5 o1 |: v; b9 a5 I. @/ s
alpha        beta        gamma        delta        epsilon        zeta        eta        theta        iota        kappa        lambda        mu
2 o: U5 I, B3 q  G* }* X4 ? ) I; `& ^! t0 f/ h- H: N' A

4 {6 g% |$ [6 b4 ^
% ~, |& n" G( z& w1 y; e5 m1 ^' x2 L , O1 ~* q9 t. ^/ J! |9 d
. H* ?; r! ~; ]8 k. H4 l% v7 f
! e1 `. l- f! P0 T1 t5 B

6 J: g$ e1 N" i6 M" y ; |  q8 c# b3 d: i
) l) ~9 l" W' u
8 k9 k8 I- Q& F/ R  {
# R  y3 Q; C) I3 u. U% P

  C# [( ^. T/ _$ s! Z, H. o# b5 O, f6 y
nu        xi        omicron        pi        rho        sigma        tau        upsilon        phi        chi        psi        omega
  R4 H: J/ K2 V8 c# i/ e有时候为了美观或特殊需要,可以采用Maple中的函数或程序设计方式控制其输出方式,如下例:6 G; _0 v+ X8 e/ n0 M
> for i to 10 do + ~6 W) I1 C  e) a; U* [
printf("i=%+2d and i^(1/2)=%+6.3f", i, eval(sqrt(i)));
9 G7 J9 ^; _- Q3 @+ jod;
" e  ?- K# L  Ji=+1 and i^(1/2)=+1.000i=+2 and i^(1/2)=+1.414i=+3 and i^(1/2)=+1.732i=+4 and i^(1/2)=+2.000i=+5 and i^(1/2)=+2.236i=+6 and i^(1/2)=+2.449i=+7 and i^(1/2)=+2.646i=+8 and i^(1/2)=+2.828i=+9 and i^(1/2)=+3.000i=+10 and i^(1/2)=+3.162/ ~3 i8 @1 ^- w0 A
+2d的含义是带符号的十进位整数,域宽为2. 显然,这种输出方式不是我们想要的,为了得到更美观的输出效果,在语句中加入换行控制符“\n”即可:! G9 M* d7 u7 E4 m5 u9 \
> for i to 10 do
) o2 N" Y3 |4 d' Q: f5 k2 oprintf("i=%+2d and i^(1/2)=%+6.3f\n", i, eval(sqrt(i)));1 D$ z* h  J5 p8 L: I  b
od;9 Q9 T3 f0 ]. E. P( L
i=+1 and i^(1/2)=+1.000
4 z  a" D7 o* m& Li=+2 and i^(1/2)=+1.414
; [/ z' j4 |7 e! o" f% Y9 P6 Ci=+3 and i^(1/2)=+1.732
, B2 \8 l+ N) |1 o* p# m/ bi=+4 and i^(1/2)=+2.0006 C1 ^& u/ I9 A! R
i=+5 and i^(1/2)=+2.2368 Q6 z* a. ~- l6 |
i=+6 and i^(1/2)=+2.449
+ x- l% `; N- v+ J# U: P$ ]i=+7 and i^(1/2)=+2.646. R) }! I9 E' b) u
i=+8 and i^(1/2)=+2.828. e6 [( `" Y& I) {
i=+9 and i^(1/2)=+3.000+ q& n0 |* m6 {6 V1 P1 x% j& d
i=+10 and i^(1/2)=+3.162
# Y/ J1 F7 i* K/ T* d' i再看下例:将输入的两个数字用特殊形式打印:4 k: u  u- N0 T' s5 r' C0 ?
> niceP:=proc(x,y)) a& j1 q: o; y2 P$ _* l
printf("value of x=%6.4f, value of y=%6.4f",x,y);
$ M; t! |4 F0 K. m& m. yend proc;
, s' R# A8 t6 \5 N* a
2 M. \% n2 @; m> niceP(2.4,2002.204);
- x* q6 p2 a. dvalue of x=2.4000, value of y=2002.2040
5 I; N7 _* x+ @4 M4 o1 p$ f1.4 Maple联机帮助
9 [" @2 j8 `/ X. Y学会寻求联机帮助是掌握一个软件的钥匙. Maple有一个非常好的联机帮助系统, 它包含了90%以上命令的使用说明. 要了解Maple的功能可用菜单帮助“Help”, 它给出Maple内容的浏览表, 这是一种树结构的目录表, 跟有…的词条说明其后还有子目录, 点击这样的词条后子目录就会出现(也可以用Tab键和up, down选定). 可以从底栏中看到函数命令全称, 例如, 我们选graphics…, 出现该条的子目录, 从中选2D…, 再选plot就可得到作函数图象的命令plot的完整帮助信息. 一般帮助信息都有实例, 我们可以将实例中的命令部分拷贝到作业面进行计算、演示, 由此可了解该命令的作用. % u& _& F' n& a- t
在使用过程中, 如果对一个命令把握不准, 可用键盘命令对某个命令进行查询. 例如, 在命令区输入命令“?plot”(或help(plot);), 然后回车将给出plot命令的帮助信息, 或者将鼠标放在选定的要查询的命令的任何位置再点击菜单中的“Help”即可.
% W6 ~0 q" N+ `: g" v9 A2  Maple的基本运算8 ~" J! D& z/ n% j/ h
2.1 数值计算问题6 K  `& q, {$ A- K7 v& \
算术是数学中最古老、最基础和最初等的一个分支, 它研究数的性质及其运算, 主要包括自然数、分数、小数的性质以及他们的加、减、乘、除四则运算. 在应用Maple做算术运算时, 只需将Maple当作一个“计算器”使用, 所不同的是命令结束时需加“;”或“:”.
0 ]/ V' N- _1 Y9 X在Maple中, 主要的算术运算符有“+”(加)、“–”(减)、“*”(乘)、“/”(除)以及“^”(乘方或幂,或记为**), 算术运算符与数字或字母一起组成任意表达式, 但其中“+”、“*”是最基本的运算, 其余运算均可归诸于求和或乘积形式. 算述表达式运算的次序为: 从左到右, 圆括号最先, 幂运算优先, 其次是乘除,最后是加减. 值得注意的是, “^”的表达式只能有两个操作数, 换言之,  是错误的, 而“+”或“*”的任意表达式可以有两个或者两个以上的操作数. 3 T! i/ x3 j1 R. x( K
Maple有能力精确计算任意位的整数、有理数或者实数、复数的四则运算, 以及模算术、硬件浮点数和任意精度的浮点数甚至于矩阵的计算等等. 总之, Maple可以进行任意数值计算. 6 P& a. e( I7 `+ c. _' Y# s
但是, 任何软件或程序毕竟只是人们进行科学研究的一种必要的辅助, 即便它有很多优点, 但也有它的局限性, 为了客观地认识数学软件、认识Maple, 下面通过两个简单例子予以说明.
8 v+ k3 m0 p+ [第一个简单的数值计算实例想说明Maple数值计算的答案的正确性:   & W, \5 Q- P0 }% s/ {
> 3!!!;
4 A5 F7 f* R! d& F1 r& N, c2601218943565795100204903227081043611191521875016945785727541837850835631156947382240678577958130457082619920575892247259536641565162052015873791984587740832529105244690388811884123764341191951045505346658616243271940197113909845536727278537099345629855586719369774070003700430783758997420676784016967207846280629229032107161669867260548988445514257193985499448939594496064045132362140265986193073249369770477606067680670176491669403034819961881455625195592566918830825514942947596537274845624628824234526597789737740896466553992435928786212515967483220976029505696699927284670563747137533019248313587076125412683415860129447566011455420749589952563543068288634631084965650682771552996256790845235702552186222358130016700834523443236821935793184701956510729781804354173890560727428048583995919729021726612291298420516067579036232337699453964191475175567557695392233803056825308599977441675784352815913461340394604901269542028838347101363733824484506660093348484440711931292537694657354337375724772230181534032647177531984537341478674327048457983786618703257405938924215709695994630557521063203263493209220738320923356309923267504401701760572026010829288042335606643089888710297380797578013056049576342838683057190662205291174822510536697756603029574043387983471518552602805333866357139101046336419769097397432285994219837046979109956303389604675889865795711176566670039156748153115943980043625399399731203066490601325311304719028898491856203766669164468791125249193754425845895000311561682974304641142538074897281723375955380661719801404677935614793635266265683339509760000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000+ g/ J7 z: Y8 p6 E1 T. o" A/ t* I/ ~
上述运算结果在IBM PC机(1G, 128M)上计算只需要0.01秒, 得到如此复杂的结果(1747位), 一个自然的问题是: 答案正确吗?+ d9 D" V7 e  A5 b! k4 N% y
为了回答这个问题, 我们借助于数值分析方法, 由Stiring公式
+ E3 H5 w2 ?  R$ U 9 m9 P9 L5 Y  o; Y: Z- L
可得:  , 前三位数字与Maple输出结果相同, 且两者结果均为1747位. 另外, 在720!的计算中, 5的因子的个数为:   
% `6 F0 O( y3 Y$ s9 f2 m1 h: ^
3 I" F, [# Z  Y* f2 f这些5与足够多的2相乘将得到178个0, 而Maple的输出结果中最后178位数为零. 由此, 可以相信Maple结果的正确性. $ Y  E( ^- F# }: _* o
另一个例子则想说明Maple计算的局限性:   5 B% M: B# ~9 f( ]9 h
  
# a/ J  w5 |& P! S0 H4 \. iMaple在处理问题时, 为了避免失根, 从不求算术式的近似值, 分数则化简为既约分数. 因此, 在Maple中很容易得到:   
; d3 x% u# L7 D3 g* ]3 l' T 4 {8 W, s  d4 D6 V  |/ `9 t9 y5 O
显然这是错误的. 这一点可以从代数的角度予以分析.
6 R: b9 \4 I/ G& ?# v不妨设 , 则 , 即 , 显然 有3个结果, -2是其实数结果. & u1 u$ [; i$ R. C! a  {) F
另一方面, 设 , 则 , 即:
5 N$ u* s& A- p7 [- [
4 h1 s7 r/ L8 `" |' m( @显然 有6个结果, -2、2是其实数结果.
4 i) i1 z$ g/ d7 C, N6 `5 c这个简单的例子说明了Maple在数值计算方面绝对不是万能的, 其计算结果也不是完全正确的, 但是, 通过更多的实验可以发现: Maple只可能丢失部分结果, 而不会增加或很少给出完全错误的结果(如上例中Maple的浮点数结果皆为 ). 这一点提醒我们, 在利用Maple或其他任何数学软件或应用程序进行科学计算时, 必须运用相关数学基础知识校验结果的正确性.   z% `  ^& }% t) H; K, P  x
尽管Maple存在缺陷(实际上, 任何一个数学软件或程序都存在缺陷), 但无数的事实说明Maple仍然不失为一个具有强大科学计算功能的计算机代数系统. 事实上, Maple同其他数学软件或程序一样只是科学计算的一个辅助工具, 数学基础才是数学科学中最重要的.
4 X5 S# w- g. d& X% _+ D+ D2.1.1 有理数运算
3 s' W' g4 x9 d; U+ T作为一个符号代数系统, Maple可以绝对避免算术运算的舍入误差. 与计算器不同, Maple从来不自作主张把算术式近似成浮点数, 而只是把两个有公因数的整数的商作化简处理. 如果要求出两个整数运算的近似值时, 只需在任意一个整数后加“.”(或“.0”), 或者利用“evalf”命令把表达式转换成浮点形式, 默认浮点数位是10 (即: Digits:=10, 据此可任意改变浮点数位, 如Digits:=20).
( u" @2 W2 @4 c! `" y> 12!+(7*8^2)-12345/125;
3 N; K" M+ Y# a. ^# i; S: j . G8 M1 [" @1 j% O8 T' M
> 123456789/987654321;: p$ ^! P) X0 r1 G2 R2 E
+ ]4 C* [- l# S- x
> evalf(%);" G- M7 _2 P. ?# \7 n

2 K) G$ m" R- h# z) L4 p2 K5 g> 10!; 100*100+1000+10+1; (100+100)*100-9;
' |6 H( ?5 |" w/ Z# o ! A9 X1 t% r- Z. D4 f3 {

" p4 l" _" @( b) c$ M
. |) z) F( Q2 V, L: f4 G7 f> big_number:=3^(3^3);
: q  e' m3 J  c: K( q4 k) v  [ 6 {# @3 Z: ^& e' F7 C" e$ t; h3 ^
> length(%);  E9 H$ w- x. R8 _- s
, u! {% U+ a& `: \
上述实验中使用了一个变量“big_number”并用“:=”对其赋值, 与Pascal语言一样为一个变量赋值用的是“:=”. 而另一个函数“length”作用在整数上时是整数的十进制位数即数字的长度. “%”是一个非常有用的简写形式, 表示最后一次执行结果, 在本例中是上一行输出结果. 再看下面数值计算例子:   
4 N) @" r, b7 Y    1)整数的余(irem)/商(iquo)
( c0 W$ a+ k" S命令格式:   9 S/ k! ?  C' M' A1 G, o
irem(m,n);        #求m除以n的余数$ F% |' N9 E$ E) B
irem(m,n,'q');    #求m除以n的余数, 并将商赋给q* K, f$ T# r7 k0 ~: m! d
iquo(m,n);        #求m除以n的商数. C  n& Q' y, X* F4 [, ?1 l4 F0 c
iquo(m,n,'r');    #求m除以n的商数, 并将余数赋给r- W, y) N& z# s7 l" k' R
其中, m, n是整数或整数函数, 也可以是代数值, 此时, irem保留为未求值.
; M/ w  y6 J2 s> irem(2002,101,'q'); # 求2002除以101的余数, 将商赋给q/ {6 C; x1 j# _& e2 F

+ }0 v. g1 r, |, f& N% e> q; #显示q, w* s! f2 q: A9 T0 V; y

" E/ d  D& n5 j# Z( k: a0 k( R> iquo(2002,101,'r'); # 求2002除以101的商, 将余数赋给r7 o5 ?/ v5 p2 O; ~* m; R; h

6 a' {' z% w1 Z* e> r; #显示r# }; U1 f& q3 q1 B  d

, Y8 p/ h: a8 `7 }5 [$ K+ \- d> irem(x,3);
6 u( Y  t" h5 ]/ `! \) W   Y$ g$ S5 ]; E+ p
2)素数判别(isprime)
( \' G3 A' Q$ |素数判别一直是初等数论的一个难点, 也是整数分解问题的基础. Maple提供的isprime命令可以判定一个整数n是否为素数. 命令格式: isprime(n); + S8 ?0 D" n8 P: @, e
    如果判定n可分解, 则返回false, 如果返回true, 则n“很可能”是素数.
  ~) B1 c& p' `. H% n> isprime(2^(2^4)+1);0 o; Q. o( x) ^1 p( U4 X

4 u, A4 l/ ~/ A! v> isprime(2^(2^5)+1);7 D; G' }3 k: T; e* _
! C( O+ n5 Q4 }$ n2 D3 N0 x) D
上述两个例子是一个有趣的数论难题。形如 的数称为Fermat数, 其中的素数称为Fermat素数, 显然, F0=3、F1=5、F2=17、F3=257、F4=65537都是素数. Fermat曾经猜想所有的Fn都是素数, 但是Euler在1732年证明了F5=641•6700417不是素数. 目前, 这仍是一个未解决的问题, 人们不知道还有没有Fermat素数, 更不知道这样的素数是否有无穷多. + Q8 L9 I/ G) C0 K) e8 ]
3) 确定第i个素数(ithprime)
  a5 }( l4 d$ _& E若记第1个素数为2,判断第i个素数的命令格式: ithprime(i);    ' J8 f) W6 R: @' [5 P
> ithprime(2002);. k6 b% L  `% }, E# M3 H7 V" d9 T
3 n1 K7 `; b9 N$ o
> ithprime(10000);  j3 f( u  y2 m: {
% S. N0 Y- Y" N1 T
4) 确定下一个较大(nextprime)/较小(prevprime)素数' u. W) N  q" F0 c& }$ k
当n为整数时,判断比n稍大或稍小的素数的命令格式为:   
( a- G8 \# i+ {! M# k7 O* `nextprime(n);  
$ k) ^' x+ G) c  Y5 q& j( u* j0 ?prevprime(n); * K2 G( a; _5 w$ w1 C
> nextprime(2002);
4 Z6 f+ g1 w* V# u 6 o& U# r* g( y
> prevprime(2002);6 Q) B* t$ d" t5 u3 j

) T# f* d) s; A/ t+ w5) 一组数的最大值(max)/最小值(min)- Q9 b8 J/ ]6 V6 c
命令格式: max(x1,x2,…,xn);   #求x1,x2,…,xn中的最大值
5 E( p9 x2 s# W5 A! }             min(x1,x2,…,xn);   #求x1,x2,…,xn中的最小值1 ]5 _% ~" T- r
> max(1/5,ln(3),9/17,-infinity);# l8 X. K/ Q5 P5 A& j, \  o
  R) X) {$ ?0 f2 l0 R, V4 i
> min(x+1,x+2,y);
8 ~  d4 ~6 _9 B& b6 s
3 V/ d( G3 b* G/ X8 C+ ^6)模运算(mod/modp/mods)
: _+ U5 Y+ c5 u( J4 ?+ Z命令格式:  e mod m;    # 表达式e对m的整数的模运算9 i- \: X# r# H4 D( I4 n; C6 H, N
modp(e,m);  # e对正数m的模运算
+ ?+ W0 V  Y  P) amods(e,m);  # e对m负对称数(即 -m)的模运算
: _' |3 L4 w; H$ A) R! C5 ``mod`(e,m);  # 表达式e对m的整数的模运算, 与e mod m等价
3 n% A0 U% \# b2 c" G% F$ c值得注意的是, 要计算i^n mod m(其中i是一整数), 使用这种“明显的”语法是不必要的, 因为在计算模m之前, 指数要先在整数(可能导致一个非常大的整数)上计算. 更适合的是使用惰性运算符“&^”即: i &^n mod m, 此时, 指数运算将由mod运算符智能地处理. 另一方面, mod运算符的左面优先比其他运算符低, 而右面优先高于+和-, 但低于*和/. / R% u" q- F! H1 ]3 B) |
> 2002 mod 101;
7 ], }6 I$ g* T7 w' b& v' s & `3 \, Y0 z# g9 v( T$ C% i" r
> modp(2002,101);9 w8 T6 [0 W8 Z' H7 s- E0 Z4 l
: Z- p# n3 l5 H& y1 G" C' z
> mods(49,100);! {7 a; g) s7 Z! a

. Y4 q5 K# F; E8 S  R8 i> mods(51,100);: b7 `$ |) @. W& X
- s5 A: f+ q6 ~' u. L6 R
> 2^101 mod 2002;  # 同 2 &^101 mod 2002;
/ o1 v( o, l/ j$ B) ?. D
3 `! A  t$ N* p3 P0 ?7)随机数生成器(rand)
% F/ I' c) P) \& Y4 {命令格式:   3 W1 y% T6 {9 ~6 z& w: N( x
rand( );    #随机返回一个12位数字的非负整数2 |5 m  H9 }$ J6 M0 b8 C3 ]
rand(a..b);  #调用rand(a..b)返回一个程序, 它在调用时生成一个在范围[a, b]内的随机数
" q8 x' E/ R) E> rand();. M1 w- T$ i3 y6 A
: j/ X2 R( H3 b1 z! {) \
> myproc:=rand(1..2002):
8 Y0 Y4 C+ b5 Z) `. @" O> myproc();
* Y( L' P5 v( w9 o* s' r( q+ s# h8 E
0 N0 P( V( `& n$ I0 ^> myproc();
5 D* s& G( u! L: A% E, X
5 k0 ?& u: I  L7 J+ U, |: \  _    注意, rand(n)是rand(0..n-1)的简写形式.0 w( H: x" c9 S
2.1.2 复数运算# ^$ \1 J4 K! W( ^5 y# `% }
复数是Maple中的基本数据类型. 虚数单位i在Maple中用I表示. 在运算中, 数值类型转化成复数类型是自动的, 所有的算术运算符对复数类型均适用. 另外还可以用Re( )、Im( )、conjugate( )和argument( )等函数分别计算实数的实部、虚部、共轭复数和幅角主值等运算. 试作如下实验:   
( z* i) v$ q& A" i3 ]8 b1 N  ]> complex_number:=(1+2*I)*(3+4*I);
4 d5 x: B& v" C% {6 }
3 @& \( ?$ I: }  h; s> Re(%);Im(%%);conjugate(%%%);argument(complex_number);3 R' f# R8 I0 g& e  q0 [5 W& R

# s* B' }/ b4 l) q( o* T9 J0 V0 r 3 e& s$ t9 f0 {# d, @
1 i; W$ e* H& w$ h

4 l* v( }! W) J4 g- o9 l, h# F值得注意的是上行命令中均以“;”结束, 因此不能将命令中的2个%或3个%(最多只能用3个%)改为1个%, 因为%表示上一次输出结果, 若上行命令改为“,”结束, 则均可用1个%.
, y  r1 M( r- ^4 q为了在符号表达式中进行复数运算, 可以用函数evalc( ), 函数evalc把表达式中所有的符号变量都当成实数, 也就是认为所有的复变量都写成 的形式, 其中a、b都是实变量. 另外还有一些实用命令, 分述如下:   
+ `1 O  @0 q; E. H- H( _1) 绝对值函数: [& \2 d7 w  w( ], g# R5 ^1 z
命令格式: abs(expr);  ; Z. W$ M: j( Z4 v
当expr为实数时,返回其绝对值,当expr为复数时,返回复数的模.+ y' P4 ~2 g6 t5 e
> abs(-2002);    #常数的绝对值
+ @( [  W8 t, |6 h
' I4 m* G7 J$ O# ~! [' K> abs(1+2*I);   #复数的模
2 m9 T: T" y  Y0 X( D - d7 |  r* F- i3 c/ J
> abs(sqrt(3)*I*u^2*v);  #复数表达式的绝对值: V1 R# O! W0 I/ {* o: y; y1 Z9 e
; t, `/ f4 F& U! d1 O
> abs(2*x-5);   #函数表达式的绝对值5 W3 M* L  ^) }8 G3 N, n! ]

8 X# c" g: o3 [% Q# o4 I& ^2)复数的幅角函数7 n  n7 Z, D1 Y
命令格式:   argument(x);  #返回复数x的幅角的主值) @! D- B8 D2 R
> argument(6+11*I);, v) E& B# i- O! |

- ~0 A( K% S7 Q$ q% \( X! A  T! W5 A> argument(exp(4*Pi/3*I));
3 {0 Q2 T. Z/ r; D4 l
9 R6 X; j* |. W* X2 W3)共轭复数: |* W/ w5 ^* T  Y4 f
命令格式:   conjugate(x);  #返回x的共轭复数
" }# X4 D9 R: i> conjugate(6+8*I);9 R7 D! g1 G* W; _; T" ^2 ]% l

& F* i1 `/ ~5 J' t4 k7 J0 D! Y5 F> conjugate(exp(4*Pi/3*I));% ]6 e: b  F& B4 Z; s' O9 j0 m
  b1 Q: p* s4 ^! l! g
2.1.3 数的进制转换; ~2 @8 D( J: P8 l& t' P. y
数的进制是数值运算中的一个重要问题. 而在Maple中数的进制转换非常容易, 使用convert命令即可.
7 s3 H+ e' a3 ?+ T命令格式:   convert(expr, form, arg3, ...);    ) @+ I8 {, s: c$ f8 W
其中, expr为任意表达式, form为一名称, arg3, ... 可选项. 9 W, z* x/ {% r' f% _
下面对其中常用数的转换予以概述. 而convert的其它功能将在后叙章节详述. % r5 |& x8 e, c2 u! Q' k3 j
    1)基数之间的转换
  n  _! P" p; W1 n2 h命令格式:   
8 H) Q, s6 B# i# v0 f9 ?2 {/ Lconvert(n, base, beta);      #将基数为10的数n转换为基数为beta的数4 _& P) z7 f6 f3 S6 J
    convert(n, base, alpha, beta);#将基数为alpha的数字n转换为基数为beta的数  Z9 Y) v: b" N8 b/ Q( g7 r
> convert(2003,base,7); #将10进制数2002转换为7进制数, 结果为: (5561)7$ q( r$ I0 ?, ^
; b$ N: g, p  G# v* T5 R
> convert([1,6,5,5],base,7,10); #将7进制数5561转换为10进制数
0 D, I8 h* K$ Z3 r) y( G " }" n0 W- u$ o0 i8 K% p
> convert(2002,base,60);       #将十进制数2002转换为60进制数, 得33(分钟)22(秒)
0 S2 d/ F9 w4 x- l
: X5 W. k( z$ A& f4 B. o  v" n    2)转换为二进制形式2 j. n; D3 D2 T' E( C! N% U1 ^
命令格式: convert(n, binary);
( l# n1 n- ]7 V- s* L. D3 C其功能是将十进制数n转换为2进制数. 值得注意的是, 数可以是正的, 也可以是负的, 或者是整数, 或者是浮点数, 是浮点数时情况较为复杂.
9 A5 w. `, ?2 v$ a: k> convert(2002,binary);   ) ]6 ~/ s& I" a8 L9 v* s! x
. D. P: c. p; H! |
> convert(-1999,binary); 8 G3 B* ~# a0 |: P' `0 r

7 X. b+ v, D" ~5 {1 H1 d> convert(1999.7,binary);
$ A7 ?# A) ?2 A) x" q 2 ]. O7 p. x$ U, B3 p; `" W
3)转换为十进制形式; H+ b: v2 n. ?' M% _
其它数值转换为十进制的命令格式为:   # u0 D9 `0 O0 u( ~
convert(n, decimal, binary);   #将一个2进制数n转换为10进制数1 n8 Q( ?% j' ~8 U8 {
    convert(n, decimal, octal);    #将一个8进制数n转换为10进制数. H8 v; v$ y$ M
    convert(string, decimal, hex);  #将一个16进制字符串string转换为10进制数
5 u, k5 B; Q% y8 n' q> convert(11111010010, decimal, binary);   
% B# v: V2 f; d- z% _5 v/ D
; U8 l3 a5 B0 D; P2 R" M> convert(-1234, decimal, octal);           
$ l6 Q, V+ E2 D  w: X. R5 G9 n. U
, q" J0 |, k# ~5 \% S> convert("2A.C", decimal, hex);         
% z0 `9 l7 s3 `1 Q! ~; q   g6 }, ~: M% |5 B  p
4) 转换为16进制数5 e% q! v! ^) C3 M
将自然数n转换为16进制数的命令格式为: convert(n, hex);     Z8 K% `8 U( i  B1 ]" q
> convert(2002,hex);  convert(1999,hex);
3 g6 O7 b( D+ U; S+ P3 u3 \ : s) B. r% J5 \
1 b. Y: Q/ V7 X9 E
5)转换为浮点数$ q+ X5 ?6 r$ G& @, u2 B' ]
命令格式: convert(expr, float);( p1 t  u5 w9 c) z# F3 B
注意, convert/float命令将任意表达式转换为精度为全局变量Digits的浮点数, 且仅是对evalf的调用. 8 F. J0 O- f7 B! J
> convert(1999/2002,float);
. K# E1 V$ \, {6 M
& N! w/ _- T6 b; m/ s- g& ?8 I> convert(Pi,float);
" E* T5 O6 s- Z2 A: f 4 y% K6 a0 X6 E- ?; A
2.2 初等数学. _  E3 R3 G  J  T! M
    初等数学是数学的基础之一, 也是数学中最有魅力的一部分内容. 通过下面的内容我们可以领略Maple对初等数学的驾驭能力, 也可以通过这些实验对Maple产生一些感性认识. ; Z' ^3 W# ~' `1 x' D/ h
2.2.1 常用函数/ M+ l; Q$ v8 ?
作为一个数学工具, 基本的数学函数是必不可少的, Maple中的数学函数很多, 现例举一二如下:   
, Y" m/ W8 u. v+ W; O指数函数: exp
6 j, ~+ q. e" o9 a+ C一般对数: log[a]( D$ |: j# d7 V* _( v0 ~* e: I
自然函数: ln
4 _* Y- j1 f; L8 i3 ?7 {4 b# x' u常用对数: log10
- [5 @* f) T/ Y平方根: sqrt: r9 b8 \+ j: A6 Q4 ]
绝对值: abs% y$ g6 ?, K  L
三角函数: sin、cos、tan、sec、csc、cot2 F% d( B2 n8 I: g$ Q0 D2 G' S
反三角函数: arcsin、arccos、arctan、arcsec、arccsc、arccot* n$ ^+ ~) y) l  u
双曲函数: sinh、cosh、tanh、sech、csch、coth" r8 M* P0 ~2 l# A% H4 p
反双曲函数: arcsinh、arccosh、arctanh、arcsech、arccsch、arccoth
1 n- G- v* f, c; k# ]3 [1 \贝赛尔函数: BesselI、BesselJ、BesselK、BesselY, v. T, B1 V" @3 t6 z
Gamma函数: GAMMA
. x; n2 @* [9 S0 I误差函数: erf
+ h0 m- j: O$ j3 T# r+ h函数是数学研究与应用的基础之一, 现通过一些实验说明Maple中的函数的用法及功能. & T4 N6 h# b: |
1) 确定乘积和不确定乘积
2 W( b2 N( t0 d2 }3 X命令格式: product(f,k);  
1 b2 K/ t. Y8 _0 Gproduct(f,k=m..n);  
% P# T% c; t& _3 d# F6 ~product(f,k=alpha);
' K  P% V+ ]) k' ^- a8 ?product(f,k=expr);; G* \9 H7 F) q: |
其中, f—任意表达式, k—乘积指数名称, m,n—整数或任意表达式, alpha—代数数RootOf,     expr—包含k的任意表达式.   D/ D* J, d2 a) p/ ~+ B
> product(k^2,k=1..10);   #计算 关于1..10的连乘4 W* g2 n1 m, B# o7 U/ p

1 i/ ^; F* X4 m% G4 T& Y: w& q7 n> product(k^2,k);         #计算 的不确定乘积: ^! I0 Z  d5 Y( Q2 G

- h7 a% Z0 Q  B; [; U' y> product(a[k],k=0..5);    #计算ai(i=0..5)的连乘
8 n' I" P) e2 [) P7 k
& E$ U7 b. a7 I0 ^! c> product(a[k],k=0..n);    #计算ai(i=0..n)的连乘
& }+ s6 o% Q8 ~& F
! x/ H1 g9 h6 d; m/ S' P5 }1 [* k2 Q5 a> Product(n+k,k=0..m)=product(n+k,k=0..m);   #计算(n+k)的连乘, 并写出其惰性表达式
( t) u' S: g" D; f9 x8 \9 I  ^
+ [0 n0 i# i  w* N: R> product(k,k=RootOf(x^3-2));     #计算 的三个根的乘积$ Y! h, z' M  L) o& ^

" ~8 k! I/ k& M" D% d4 g0 F9 B    product命令计算符号乘积, 常常用来计算一个公式的确实或不确实的乘积. 如果这个公式不能求值计算, Maple返回 函数. 典型的例子是:   $ I% _  }: v5 S5 n. j' c4 j8 Q
> product(x+k,k=0..n-1);
# \8 o7 f7 x0 _( }7 y
! s2 f3 |9 I* V2 R) g如果求一个有限序列值的乘积而不是计算一个公式, 则用mul命令. 如:   0 x# z0 a/ O: S# [: l8 K
> mul(x+k,k=0..3);2 {" f: b8 d4 x# G, x* Z6 B+ F

7 E' M, ]) ?5 P, [# h. U2)指数函数
7 c: {/ P) ?& E  o: I( ^* l计算指数函数exp关于x的表达式的命令格式为: exp(x); 6 Y5 k  z; i! `2 {/ I- G5 V
> exp(1);8 E4 E2 R4 P2 S

' W3 G' u  o) y" I7 Z> evalf(%);
% j/ d4 j: X6 _4 F
8 {- Y/ i+ L) j1 d4 }, A" a  u> exp(1.29+2*I);
3 j* ^) ?1 N4 u. }% i: H; c ( n5 ], a+ h* E: x. H  [
> evalc(exp(x+I*y));
# {6 K. t0 n, M: x5 o( {' y: P
* ~$ q; D) F8 t1 y3)确定求和与不确定求和sum% _, o9 `$ E, F7 b# H- [8 Q! N
命令格式: sum(f,k);  
/ U) u9 a9 `$ R+ ^; ^: r2 ~* xsum(f,k=m..n);  
9 n" U- H6 }; \' ^6 m$ vsum(f,k=alpha); : O. \1 v  ]1 q
sum(f,k=expr);
2 G/ F1 x2 v/ S其中, f—任意表达式, k—乘积指数名称, m,n—整数或任意表达式, alpha—代数数RootOf,     expr—不含k的表达式. 3 H9 V, i( |: A* _8 @% f' N1 h
> Sum(k^2,k=1..n)=sum(k^2,k=1..n);, P1 g! m7 \$ C2 `; X; a
+ x/ {7 I2 ]! h. V2 }8 W4 A% y' ?# d0 `
> Sum(k^3,k=1..n)=sum(k^3,k=1..n);9 `4 h5 o* l! U2 e/ `$ l/ j

+ m% x2 n& h' c" b' ^5 X( T' z" j> Sum(k^4,k=1..n)=sum(k^4,k=1..n);: I/ X* J  \! A- V% m
7 X; n" E9 ^3 z) U4 S9 y6 E
> Sum(1/k!,k=0..infinity)=sum(1/k!,k=0..infinity);
/ _- H5 e  I  N
( @% {. Q% R$ J5 L, h+ E# I> sum(a[k]*x[k],k=0..n);
9 |% p! y& r* g( h; l% e1 u, n
! s' U9 t0 Y! G4 ~, w> Sum(k/(k+1),k)=sum(k/(k+1),k);
  F2 |) _  S3 S4 h: d ) O, f% ?9 O* ?! a  Z% B5 G2 K
> sum(k/(k+1),k=RootOf(x^2-3));
8 }! _- T' U9 e ) L: V& d2 Z6 H# P) b, L
sum函数可计算一个公式的确定和与不确定和, 如果Maple无法计算封闭形式, 则返回未求值的结果. 值得注意的是, 在sum命令中将f和k用单引号括起来, 可避免过早求值. 这一点在某些情况下是必需的.
% I" L- d2 n- m9 N# E% Q, D( d> Sum('k','k'=0..n)=sum('k','k'=0..n);# e( [2 N% r0 Z9 R7 d: L( H1 u
% q9 C) j; e" N1 c! {/ @/ b
如果计算一个有限序列的值, 而不是计算一个公式, 可用add命令. 如:   , i4 q' t; E! Z) D) G& J
> add(k,k=1..100);
8 ~+ G' k1 `8 N' l) S# Z3 \* M2 r
: b" y) \! i5 m7 n尽管sum命令常常用于计算显式求和, 但在程序设计中计算一个显式和应该使用add命令. * O$ w) C. m" V. ?7 |% O1 M6 {
另外, sum知道各种求和方法, 并会对各类发散的求和给出正确的结果, 如果要将求和限制为收敛求和, 就必须检查显式的收敛性. ! S# f: W, _) @, |/ i( W! R
3)三角函数/双曲函数
3 \  V0 ^- o: r$ ~' a. c* h4 Y命令格式:   sin(x);   cos(x);   tan(x);   cot(x);   sec(x);   csc(x);
1 i" S* D, J, n; |3 v4 t          sinh(x);  cosh(x);  tanh(x);  coth(x);  sech(x);  csch(x);
  g2 i) s, v8 ~0 \9 g+ ]7 ?# A/ d其中, x为任意表达式. . }" Z, y& Z+ y4 d! d& u
值得注意的是三角函数/双曲函数的参数以弧度为单位. Maple提供了利用常见三角函数/双曲函数恒等式进行化简和展开的程序, 也有将其转化为其它函数的命令convert.) {5 s2 E  x; \  x3 P
> Sin(Pi)=sin(Pi);. ^, Y/ K  L# B9 Z. t/ t
/ u9 C8 x) A" S/ [% b8 ?
> coth(1.9+2.1*I);& H  [! |. n# _: {
$ N& f4 K% e+ o
> expand(sin(x+y));     #展开表达式
4 y; }# y" ?' b* t0 c 8 ?' E. d" d8 |  e) T
> combine(%);        #合并表达式0 v6 w0 d" S- G1 e
+ n$ s8 V- P- y2 D& n
> convert(sin(7*Pi/60),'radical');
2 H! \' o) k4 Q: R5 i
. c' m$ x- j( _> evalf(%);
6 I; l2 w- _) K  U! v 0 Y+ l) ~$ Z" m- t& _( d( C
但有趣的是, combine只对sin, cos有效, 对tan, cot竟无能为力.6 a& {' Y8 O* S* F; [
4)反三角函数/反双曲函数
* n% O0 y8 T0 q* {命令格式: arcsin(x);   arccos(x);   arctan(x);   arccot(x);   arcsec(x);   arccsc(x);7 n, H. f' c  B  K
     arcsinh(x);  arccosh(x);  arctanh(x);  arccoth(x);  arcsech(x);  arccsch(x);   7 X" B- A$ g/ F6 I5 A/ |; n
arctan(y,x);$ |  ]' `" u, D2 U( ^& v
其中, x, y为表达式. 反三角函数/反双曲函数的参数必须按弧度计算.
" P  V$ @  y, E算子记法可用于对于反三角函数和反双曲函数. 例如, sin@@(-1)求值为arcsin.* J- \7 n: j$ I& e0 O
> arcsinh(1);) z; I' S0 I: @# C( R
* W0 U0 g, h2 ]" F
> cos(arcsin(x));2 f2 [4 f+ x. |( g5 U, W
/ G5 q# L: Z2 J8 {$ k
> arcsin(1.9+2.1*I);
5 m  O6 M4 Q9 A$ [
6 i! h" }7 t* N9 O2 R4 R: z; i) E- @) b5)对数函数5 N6 r' p; v5 O( s
命令格式: ln(x);           #自然对数
) H' j) a; @3 ]" ?7 `5 Flog[a](x);        #一般对数4 `2 f1 u" H1 z( m
log10(x);        #常用对数
9 d! B. ?% H+ C$ J' [4 V" R一般地, 在ln(x)中要求x>0. 但对于复数型表达式x, 有:   ; v( G1 z5 J7 k' u
  (其中,  )
1 L" U' Y$ n, F9 D8 V' {. ]> ln(2002.0);
# a, r9 F- ^# H9 B
% p* O- ?: F; R+ `> ln(3+4*I);$ k1 [% Z* P  k$ E: ]2 V: F
! x/ p8 m! }! ]' S
> evalc(%);    # 求出上式的实部、虚部5 V# J. [0 k  h+ ~/ v% Z

" ~/ Y7 u8 D3 _/ C9 f> log10(1000000);
7 s: |  Q- c# g4 b/ H, j
. X5 ~- h/ i5 n! B( _> simplify(%);   #化简上式! w- ^, I6 h& e0 @4 ?

) u2 K* x, C! L+ w" Y# E8 o7 g* c2.2.2 函数的定义
) V* Z( B3 c2 k" b' wMaple是一个计算机代数系统, 带未知或者已知字母变量的表达式是它的基本数据形式. 一个简单的问题是, 既然表达式中可以包含未知变量, 那么它是不是函数呢?试看下面一个例子:   
8 d( T6 Z& g' `1 B1 l) W5 i& A* |- N> f(x):=a*x^2+b*x+c;) U" i4 K" h1 ]3 F( A
! R" i% N6 c0 [7 d7 X
可以看出, Maple接受了这样的赋值语句, 但f(x)是不是一个函数呢?要回答这个问题,一个简单的方法是求函数值:   , a0 T2 I: v2 }1 W3 ^( B0 a% O: l
> f(x),f(0),f(1/a);6 ~: I8 y7 e/ _+ M  |/ F9 H& O; v

; _5 a1 U8 G  C5 t6 b. k由上述结果可以看出, 用赋值方法定义的f(x)是一个表达式而不是一个函数, 因为f(x)不能把所定义的“自变量”或者“参数”转换成别的变量或表达式. 但从赋值“过程”可以看出, f(x)虽然也算是一个“函数”, 但却是一个没有具体定义的函数:   
: R* o8 |& S( R" V1 e' z; c> print(f);* l1 s( B) t$ z1 f# e/ C

8 S* J0 E( o- Z7 D事实上, 我们所做的赋值运算, 只不过是在函数f的记忆表(remember table)中加入了f(x)在x上的值, 当我们把自变量换作0或1/a时, f(x)的记忆表中没有对应的表项, 所以输出结果就是抽象的表达式.
* m& b. d5 |' z7 ^$ l在Maple中, 要真正完成一个函数的定义, 需要用算子(也称箭头操作符):   
7 C3 B. U. V' q( |: {* U+ I9 X. b> f:=x->a*x^2+b*x+c;
7 T7 z% F3 o# I( W. M1 [
0 ^+ v, p9 }3 j0 [6 A> f(x),f(0),f(1/a);0 x, {$ G5 R, n9 ^
3 d* ]( M/ M+ L
多变量的函数也可以用同样的方法予以定义, 只不过要把所有的自变量定成一个序列, 并用一个括号“()”将它们括起来(这个括号是必须的, 因为括号运算优先于分隔符“,”). - [* r. U1 J  k% F+ H
> f:=(x,y)->x^2+y^2;5 y. S# k; e5 y# \8 U
$ x9 O# J+ ~7 L% Y5 s& v
> f(1,2);
- a+ |$ e) G) i
$ Q0 }4 f3 m7 l> f:=(x,y)->a*x*y*exp(x^2+y^2);5 ~5 Y2 w' V! \

; |( g% W4 i- H% Q# y0 W8 F1 L( h* j综上所述, 箭头操作符定义函数的方式一般为:   7 e5 n& W9 ?  J4 I0 E
一元函数: 参数->函数表达式
- W* \# ~. o4 f/ n' r多多函数: (参数序列)->函数表达式
4 H& A5 S6 F  E1 ?8 x2 @无参数函数也许不好理解, 但可以用来定义常函数:   
& C  [: E$ E# f& P& ]" V> E:=()->exp(1);3 U( h2 _; `3 C* O4 |

0 N2 S7 e2 J+ t$ C' w  P> E();- |; l. g) L0 C4 }1 U) ?

2 [( K4 P4 ^( t' `& N) f> E(x);
( E' s! U- L9 p7 `7 R & E' W4 n7 ^6 h. e* B
另一个定义函数的命令是unapply,其作用是从一个表达式建立一个算子或函数. 8 u. v6 h- C5 F( \
定义一个表达式为expr的关于x的函数f的命令格式为:  f:=unapply(expr, x);          6 t  o+ B3 q9 J" S# }9 a* ]9 Y0 Y
定义一个表达式为expr的关于x,y,…的多元函数f的命令格式为:  f:=unapply(expr, x, y, …);     ; O  ~9 S# Q) \' |2 c+ j
> f:=unapply(x^4+x^3+x^2+x+1,x);
! e( _% S0 o3 L6 t- [/ M , M: Q0 K/ E$ j( O" Z! G% D) a% d
> f(4);
; O& |+ b) e! x5 F# D% _% X
9 ~$ b# ^3 c4 W; M* w> f:=unapply(x*y/(x^2+y^2),x,y);7 D9 g% M  U3 C5 X

9 k8 A1 j' U& V% t7 h0 S+ n. E> f(1,1);9 q2 i* u& v3 Q) M. X6 Y6 t2 n

9 N0 y( J. Z/ h: a5 G' e3 M借助函数piecewise可以生成简单分段函数:1 W6 Q9 I5 Z1 o
> abs(x)=piecewise(x>0,x,x=0,0,x<0,-x);+ d$ t# D( {4 a: f1 p( y, k$ C/ @

; e5 h% T' d( ^5 Q: D3 [( h6 a清除函数的定义用命令unassign.
+ |# r- p: b- Q7 b+ A1 c& D4 ^> unassign(f);3 s4 d4 h6 y7 f' d
> f(1,1);7 C" Y  L2 p# }; U

' `+ O8 `3 d% f7 s" `) r* F除此之外, 还可以通过程序设计方式定义函数(参见第6章).
. _, S) U4 o$ F9 i+ r7 r定义了一个函数后, 就可以使用op或nops指令查看有关函数中操作数的信息. nops(expr)返回操作数的个数, 函数op的主要功能是获取表达式的操作数,其命令格式为:6 c. f( `. Z0 O9 O+ q+ |
op(expr);         
" ?: N/ W9 p- T. m$ Q! J- xop(i, expr);         
3 v' |6 \/ W# Q1 n, O( ~2 K* gop(i .. j, expr);      
# [5 z! J' d2 n, \3 Znops(expr);
0 ?6 z4 r, ?6 D0 {如果函数op中的参数i是正整数,则op取出expr里第i个操作数, 如果i是负整数, 则其结果为op(nops(expr)+i+1, expr); 而i=0的情形较为复杂, 当expr为函数时, op(0, expr)返回函数名, 当expr为级数时, 返回级数的展开点(x-x0), 其它数据类型, op(0, expr)返回expr的类型. ; t) F" y5 X9 w+ I: l0 W6 \9 [$ y
命令op(i .. j, expr); 执行的结果是expr的第i到第j个操作数, i..j中含负整数时的情形同上.2 t, |2 |) }6 U: y( p* H! E
命令op(expr); 等价于op(1..nops(expr), expr); ( E* c, M1 v- X+ S- T
特别地, 当op函数中i为列表[a1, a2, ..., an], 则op([a1, a2, ..., an], expr); 等价于op(an, op(..., op(a2, op(a1, e))...)); 9 [+ b4 I0 y3 p: S- _+ c
而当expr为一般表达式时,nops(expr)命令返回的是表达式的项数, 当expr是级数时返回级数每一项的系数和指数的总和. : |7 ~# L$ T: L2 ^+ ^
> expr:=6+cos(x)+sin(x)*cos(x)^2;
; `0 N1 {' q. M) b0 x9 v( V
7 \# K' z2 f* f# R> op(expr);- d8 l$ Q; z( U6 h6 e- `' r

9 O/ B! l) m# Q> nops(expr);
6 A8 z2 `0 |; a  ]% [; G
- x: N. B5 @' u! @! x, y2 \0 `. a> p:=x^2*y+3*x^3*z+2;% ~; V5 ]; x6 y  L
& g* F7 K7 R) j2 N; d
> op(1,p);
  i- }8 o- u- l) G8 }3 T
( M1 o2 q6 ?! u) P% f. ?> op(1..nops(p),p);6 ]  O) o. }6 p' L" }+ @- e
$ D4 U: |7 m; }
> op(op(2,p));4 k6 m4 v* M" U* Z: H3 u: t

4 W. B6 N4 O7 W( P4 a  K> u:=[1,4,9];
* C) P4 T/ d9 `; p- N9 L9 f
/ l! M) N0 E1 j6 w/ N# s> op(0,u);, B. g' G1 b. t; h" P9 g7 d

  E- G* H2 E* Z( A> s:=series(sin(x),x=1,3);) W4 r: B8 p; T7 z

! w: V; q. M& M; ^% v> op(0,s);
9 o# K+ w; J$ q% P0 r5 b         ( ~* E- c. C8 q
> nops(s);
. j" H5 v% B, P  p; v8 U8 h
' q: i9 Q  e% V8 T! D6 M下面一个有趣的例子说明了Maple在处理算术运算时的“个性”:) Y2 N% }2 @1 T; M: U
> op(x*y*z);
" F. l* D! }  s 3 d  K2 o6 t3 ?% ]% e
> op(x*y*z+1);( V1 U. U: Y8 Q- P0 W+ V
# o, l% |3 z0 G2 v
2.2.3 Maple中的常量与变量名% B! |1 w& O8 P) P: Z% {; r
为了解决数学问题, 一些常用的数学常数是必要的. Maple系统中已经存储了一些数学常数在表达式序列constants中:     Z- H: b9 ]( G' s, v: t/ H2 j
> constants;
1 M) {/ A: h/ K! `0 O9 K8 x& n% r  u$ T
% u' h! H3 b6 V为了方便使用, 现将上述常数的具体含义列示如下:     u8 O3 ^# H# n8 Q
常    数        名 称        近似值* \! U! m9 u, B# K% J9 j  u
圆周率 5 b6 ?: j/ z' e. L+ ?# q2 {, s+ O
Pi        3.1415926535
* ~1 x: H( j' t1 J# s- L3 z* JCatalan常数
! o' I% ~* u5 s: J+ g( PCatalan        0.9159655942
! S4 _; a1 _3 P/ h9 p2 IEuler-Mascheroni常数
1 ?( f& g8 P2 e2 ?& _/ Bgamma        0.5772156649
; y  U6 d- |8 X' G7 V& f9 a
! R6 ?8 c( T* A0 Hinfinity       
- l6 q# b- X' s: v- S' S$ O$ z/ S# u7 [# f# w% t
需要注意的是, 自然对数的底数e未作为一个常数出现, 但这个常数是存在的, 可以通过exp(1)来获取. + d7 ?# V1 ?7 I' p) s
在Maple中, 最简单的变量名是字符串, 变量名是由字母、数码或下划线组成的序列, 其中第一个字符必须是字母或是下划线. 名字的长度限制是499个字符. 在定义变量名时常用连接符“.”将两个字符串连接成一个名. 主要有三种形式: “名.自然数”、“名.字符串”、“名.表达式”. 9 J& g) v% l; _7 q
值得注意的是, 在Maple中是区分字母大小写的. 在使用变量、常量和函数时应记住这一点. 数学常量 用Pi表示, 而pi则仅为符号 无任何意义. 如g, G, new_term, New_Team, x13a, x13A都是不同的变量名. ; m5 N1 C3 s4 Y) f7 i+ D
在Maple中有一些保留字不可以被用作变量名:   
$ e5 ~* Q8 C: z( W# {  F- D$ n8 Dby      do      done     elif     else     end        fi        for      
* l7 Z* L* V% Q* I' k" afrom    if       in       local     od     option    options     proc         6 x" n# W3 t9 H6 l9 o4 u4 b
quit    read     save     stop     then     to        while      D
* U9 }: i3 K& v: G9 TMaple中的内部函数如sin, cos, exp, sqrt, ……等也不可以作变量名.
2 q, V: T1 N2 ?! e& F1 ^# {另外一个值得注意的是在Maple中三种类型引号的不同作用:   9 ~# z3 c6 L1 ^1 n, E
`  `:   界定一个包含特殊字符的符号, 是为了输入特殊字符串用的;   
7 ~& I7 `) m8 Q( P'  ':   界定一个暂时不求值的表达式;    * b, `& v1 G' s% q0 O
"  ":   界定一个字符串, 它不能被赋值.
' B% `* o) e' _7 W) i  }: c2.2.4 函数类型转换           
1 L" h0 Q2 E# Y! N+ i函数类型转换是数学应用中一个重要问题, 譬如, 将三角函数转换成指数函数, 双曲函数转换成指数函数, 等等. 在Maple中, 实现函数类型转换的命令是convert. 命令格式:  
& X, n" G& B) j: x0 f5 o& q$ z. i    convert(expr, form);        #把数学式expr转换成form的形式. d+ }9 R* j" w; I2 X! G
convert(expr, form, x);      #指定变量x, 此时form只适于exp、sin、cos6 G% ^6 a2 l( E
convert指令所提供的三角函数、指数与函数的转换共有exp等7种:   
$ X, |9 R; ~! W# ^3 b(1) exp: 将三角函数转换成指数
: K% C9 e: B5 L' }(2) expln: 把数学式转换成指数与对数. k* K5 c8 s! f! ^6 J  ~0 t4 C" F
(3) expsincos: 分别把三角函数与双曲函数转换成sin、cos与指数的形式
1 u3 E$ Z* ^8 s" {2 n1 N(4) ln: 将反三角函数转换成对数* y7 c) Z3 ?4 {) p
(5) sincos: 将三角函数转换成sin与cos的形式, 而把双曲函数转换成sinh与cosh的形式# H0 W( b) l' I) B0 u% n
(6) tan: 将三角函数转换成tan的形式
  k' g( I0 u/ h% P0 q(7) trig: 将指数函数转换成三角函数与对数函数- f7 G$ ~/ v- e/ s5 x& i
> convert(sinh(x),exp);   #将sinh(x)转换成exp类型, J  d/ n% j. O. a7 E; D
' m$ E5 s) U5 b8 G3 u0 ~! U* W
> convert(cos(x)*sinh(y),exp);
# E% |8 n/ R: s
3 k7 O5 ~3 k4 [: c& q8 u) h> convert(cos(x)*sinh(y),exp,y);
( e6 B$ p, d8 m4 d% t( X
. x' {, C% A" Z$ k> convert(exp(x)*exp(x^(-2)),trig);
. y# ~' b3 k' o+ p0 D 6 B$ q4 g( V& O  `/ d
> convert(arcsinh(x)*cos(x),expln);
2 t% u- @% H5 v% [$ G   O6 X* w+ s9 |4 Z
> convert(cot(x)+sinh(x),expsincos);
% }* x# |3 T0 B: S+ m, E6 l
1 ^- E" G5 F- S& u6 K! r> convert(arctanh(x),ln);
2 b9 q. _  E  x
: k  ]6 P* \1 H# ^; aconvert在有理式的转换中也起着重要的作用. 在有关多项式运算的过程中, 利用秦九韶算法可以减少多项式求值的计算量. 在Maple中, 可以用函数convert将多项式转换为这种形式, 而cost则可以获取求值所需的计算量. 注意: cost命令是一个库函数, 第一次调用时需要使用with(codegen)加载. 例举如下:   
3 Y8 |( W+ H, K. @+ H$ ]> with(codegen):$ w; o/ R0 t# ^' H
> p:=4*x^4+3*x^3+2*x^2-x;
* s5 j4 X/ D3 q2 C8 T& S
9 I3 _: u; u6 _% A  V( e> cost(p);
! s0 {, F% q2 `4 O( B& Z3 e
' ^+ T2 s3 r2 L1 b8 y  Y. q> convert(p,'horner');  #将展开的表达式转换成嵌套形式& x6 K8 c7 |3 K4 y
5 b  p: A- X- T: U
> cost(%);
" z3 N5 O5 A( W. M- r2 @
5 Y0 i, M9 W! }# K同样, 把分式化成连分式(continued fraction)形式也可以降低求值所需的计算量.
8 \( i8 m. \% j> (1+x+x^2+x^3)/p;
$ G: o) ^/ _4 B6 U- Q# f
* K. Y. M8 T( B7 G/ f$ T3 a# M> cost(%);
5 |0 [0 t' X+ }! B 4 l7 ?  a7 p8 m  k. _, o5 O
> convert(%%,'confrac',x);! X, ^& r; J* ?2 Z

; B# X# g8 b) U8 N# x, {> cost(%);
# z6 X6 O/ ?3 v1 d# ~9 }: L" _! Y   D) I" U0 X& L
在某些场合下(比如求微分、积分时), 把分式化成部分分式(partial fraction)也就是几个最简分式的和式的形式也可以简化运算, 但简化程度不及连分数形式.
7 W+ j, Q% u3 L+ a' L) q7 w( H> convert(%%, 'parfrac',x);$ ^, U0 a- j6 |+ J8 ?

# C5 b. V; ^# l. C. L5 C$ K> cost(%);/ d$ x- s5 {/ A$ `2 }) j1 V0 o
" x" L, L8 b4 [
而把分数转换成连分数的方法为:, M. n8 N( S) n# f/ z, f0 f
> with(numtheory):1 a/ {/ g" b5 `( R, _  L
> cfrac(339/284);" f) N$ Z5 |1 u

+ w8 }9 Z6 f0 r5 v2 M2.2.5 函数的映射—map指令
+ @% A( P1 C( x& o- ]在符号运算的世界里, 映射指令map可以说是相当重要的一个指令, 它可以把函数或指令映射到这些结构里的元素, 而不破坏整个结构的完整性. 命令格式为:" @% g# G6 ^! O6 [1 B  d7 `
map(f, expr);      #将函数f映射到expr的每个操作数2 K# O( K5 R, q
map(f, expr, a);    #将函数f映射到expr的每个操作数, 并取出a为f的第2个自变量
( y6 I$ a' G2 h7 q! ?+ lmap(f, expr, a1, a2,…, an); #将函数f映射到expr的每个操作数, 并取a1~an为f的第2~n+1个自变量2 {0 H' X7 P  M' k0 E
map2(f, a1, expr, a2, …, an);    #以a1为第1个自变量, expr的操作数为第2个自变量, a2为
/ @: B& y6 u+ n( y* |第3个自变量…, an为第n+1个自变量来映射函数f
% r3 g2 ~' @# r% B> map(f,x1+x2+x3+x4,a1,a2,a3,a4);
6 s1 q4 B6 d4 e3 N3 G
" c: j3 D0 @6 _" K5 q1 u> f:=x->sqrt(x)+x^2;
) r3 D' J" J3 K 4 Q( U# `; S2 F8 s4 K/ t+ q
> map(f,[a,b,c]);3 [) n# c  o! a# h

8 C1 F" r7 L5 ^# l> map(h, [a,b,c],x,y); 0 Q# k+ y- U' Z, T
; V9 U* R' b  o1 Z: Q; }
> map(convert,[arcsinh(x/2),arccosh(x/2)],ln);. n  a# v8 \) D$ g9 v  c

) Z* d: ]- ]/ ?3 B> map(x->convert(x,exp),[sin(x),cos(x)]);9 i" M5 o4 |, t% j. Q
3 S4 A; r. ~1 c6 {/ Q+ x* e3 [7 M9 W
上式的映射关系可通过下式理解:6 K4 p& `3 k9 A% S/ w
> [convert(sin(x),exp),convert(cos(x),exp)];1 S6 b- L$ {8 Q$ ]. [6 y
1 g  r; P4 w* D2 }5 d3 H
> restart:
9 U3 m3 n* v2 d) emap2(f,a1,x1+x2+x3+x4,a2,a3,a4);
6 O$ W- H9 i9 Y3 x8 R
5 Q2 d4 R2 ~3 K> map2(max,k,[a,b,c,d]);
* d) B3 I7 \* R7 d6 l. F
" l0 E, l4 }6 J再看下面示例:   
) R: P& ?/ ?* ?> L:=[seq(i,i=1..10)];
) m1 l7 _4 M) w1 f) T3 [  V
8 l9 y5 _7 I! ^7 D5 x7 e3 |  @> nops(L);
- Z( i' x6 ~+ I0 t, k* S! }* ~- z+ m
9 t+ k! u* {4 B8 ~! {$ l> sqr:=(x)->x^2;
8 H" n3 ~# L0 p
* r9 v( x9 E5 i, q, M! D> map(sqr,L);
4 n% R# t: g7 m5 d# x- A5 J& u 0 X/ [* H: U) O0 q1 Q
> map((x)->x+1,L);/ q: w- u- V  X1 `( Z1 A1 u+ f
  r; A# n4 l) l
> map(f,L);$ r( n/ W4 L& `! ~% `
9 _) G9 [! {1 r2 t. \9 F
> map(f,{a,b,c});
5 H, T/ `+ |/ z: ]& ~ . Z( m# p7 W/ W7 n/ m
> map(sqr,x+y*z);
5 e" h/ E+ y$ j
  Q6 k$ N6 I1 q1 s> M:=linalg[matrix](3,3,(i,j)->i+j);
) i0 f. J# V4 q) m$ c & g+ |4 a* _2 t) y! d; v+ Y
> map((x)->1/x,M);& k4 Y, l% m+ Q; m2 y( P
3 a) p: N+ o# @" _7 v1 u
3 求 值" G% X8 A, n; p, w3 @, ~' ~2 w+ L
3.1 赋值) Y& d- T( @+ z! f2 N2 S( W7 F
在Maple中, 不需要申明变量的类型, 甚至在使用变量前不需要将它赋值, 这是Maple与其它高级程序设计语言不同的一点, 也正是Maple符号演算的魅力所在, 这个特性是由Maple与众不同的赋值方法决定的. 为了理解其赋值机制, 先看下面的例子. 8 d( W2 ~- h3 ~0 i: r# f
> p:=9*x^3-37*x^2+47*x-19;+ j, m  u% a! K! F$ ~
$ b7 w( q' b( u6 r
> roots(p);4 p' H: d, s, v1 e6 \6 z4 M

+ A/ \1 I" y3 j- R> subs(x=19/9,p);
5 E5 B8 }! C1 X- i! B4 |$ K  c 6 g" F$ u, U: J6 E
在这个例子中, 第一条语句是一个赋值语句, 它的作用是把变量p和多项式9x3-37x2+47x-19相关联, 在此之后, 每当Maple遇到变量p时就取与之唯一关联的“值”, 比如随后的语句roots(p)就被理解为roots(9x3-37x2+47x-19)了, 而变量x还没被赋值, 只有符号“x”, 通过subs语句得到将p所关联的多项式中的所有x都替换成19/9后的结果, 这正是我们在数学中常用的方法—变量替换, 但此时无论x还是p的值仍未改变, 通过“> x; p;”这样的简单语句即可验证. # K6 i1 |1 l3 J% N5 Y% J
3.2 变量代换
- |& N' [; d& b/ K: Y  O/ L在表达式化简中, 变量代换是一个得力工具. 我们可以利用函数subs根据自己的意愿进行变量代换, 最简单的调用这个函数的形式是这样的:   
+ \3 M7 v3 I: G( v7 M& Z; G1 B& W  |subs ( var = repacedment, expression);
  V6 m3 y' q4 M+ Q/ b% \2 K调用的结果是将表达式expression中所有变量var出现的地方替换成 replacement.
; F6 ]5 y. @; J) g> f:=x^2+exp(x^3)-8;
' X, `' V( l7 Y3 \3 L0 ]% f- {: l
4 o9 n  h6 X/ @; }> subs(x=1,f);0 \7 T. f" f& [$ i

1 x1 N) i2 M. o5 Z9 q2 C5 p> subs(x=0,cos(x)*(sin(x)+x^2+5));
+ p3 A* r; |2 O! ]* v8 Q . X$ \  X' e$ L5 h/ @& O2 ]
    由此可见, 变量替换只得到替换后的结果, 而不改变表达式的内容, 而且Maple只对替换的结果进行化简而不求值计算, 如果需要计算, 必须调用求值函数evalf. 如:   2 b' ?; F& |! q7 V
> evalf(%);5 Z+ g2 n; e1 ?/ V/ Y  G2 q

1 R# i6 t+ H" [6 H' h! [' t变量替换函数subs也可以进行多重的变量替换, 以两重代换为例:   / s+ n4 f- D" A4 U# }% I% W
subs (var1 = repacedment1, var2 = repacedment2, expression)
0 U: e- m2 {# Y7 q, _调用的结果和按从左到右的顺序连续两次调用是一样的, 也就是先将expression中的var1替换成replacement1, 再将其结果中的var2替换成replacement2, 把这种替换称作顺序替换;    与此相对, 还可以进行同步替换, 即同时将expression中的var1替换成replacement1, 而var2替换成replacement2. 同步替换的调用形式为:   / z& p2 p* V  [2 q( }
subs ( {var1 = repacedment1, var2 = repacedment2 }, expression)
7 n" \/ h! y& A下面通过例子说明这几种形式的替换.
1 j; P% ?3 g6 o, W> subs(x=y,y=z,x^2*y);              (顺序替换)
( r0 e% R3 T% ?4 a$ x
  I& z8 w! Z5 C0 t> subs({x=y,y=z},x^2*y);            (同步替换)
/ R! V# f! i" P9 Y- z- y 9 B2 s5 x  _5 _/ o0 r% A8 ?
> subs((a=b,b=c,c=a),a+2*b+3*c);   (顺序替换)7 `, B( {6 _7 [$ A  {/ i

- X- n6 @5 o' A; i7 o> subs({a=b,b=c,c=a},a+2*b+3*c);    (轮  换)
: L, c, Q! N4 {7 D2 D* G+ a & x7 {: ]  j2 r* j7 F
> subs({p=q,q=p},f(p,q));             (互  换)% z8 C6 X# h" z. b) w

. V7 D6 T' g+ S) m( N! t" Z3.3 假设机制$ F7 D# N" D! V3 l
Maple是一种计算机代数语言, 显然, 很多人会尝试用Maple(或其他计算机代数语言)解决分析问题. 但由于分析问题与处理问题的考虑方法不同, 使得问题的解决存在某些困难. 例如考虑方程 的解. 如果k是实数, 结果显然是x=1, 但如果k是 的复根, 为了保证解x=1的正确性, 必需添加附带条件: 也就是当 时x=1. 这是一个对结果进行正确分析的例子. 然而从代数的角度考虑这个问题时就会把k当作不定元, 此时k没有值, 从方程两端去除k的多项式是合法的, 只要这个多项式不是零多项式即可(这一点是可以保证的, 因为其所有系数不全为0). 在此情况下x=1就不需要任何附加条件. 计算机代数系统经常采用这种分析的观点. 1 T: {1 T0 J3 H7 a3 K/ @2 s0 m8 I
在Maple中, 采用分析观点解决这类带有一定附加条件的实用工具是函数assume, 其命令格式为: assume(x, prop);
) D6 n# D# ]1 t+ l) v- z函数assume界定了变量与变量之间的关系式属性. assume最普遍的用法是assume(a>0), 该语句假设符号a为一个正实常数; 若假定某一符号c为常数,使用命令assume(c,constant); 另一方面, assume可以带多对参数或多个关系式. 当给定多个参数时, 所有假定均同时生效. 例如, 要定义a<b<c, 可以用assume(a<b, b<c); 同样地, 要定义0<x<1, 可以用assume(0<x,x<1). 当assume对x作出假定时, 以前所有对x的假定都将被删除. 这就允许在Maple中先写“assume(x>0);”后再写“assume(x<0);”也不会产生矛盾.
# ^) J& w0 b% E" a! A0 o7 g> Int(exp(-s*t),t=0..infinity);
3 b# E& t# T% }9 X& u& k
( O  h/ i+ n9 G2 p( w0 N8 X3 R5 \> value(%);
- R7 \2 j5 X( }# J8 j; H4 wDefinite integration: Can't determine if the integral is convergent.5 v4 D' P$ t5 M. y
Need to know the sign of --> s/ W% U/ O7 v/ C
Will now try indefinite integration and then take limits.; h, Y' n# P6 Y- p
8 w: r; y' Q. e/ u
> assume(s>0);
' K& p* J* ?& H7 V2 `) a> Int(exp(-s*t),t=0..infinity);
" M1 N" u) Q  d( R2 W
* j, K9 s1 J- \9 }4 O0 V, w> value(%);" u. B- N! }6 c4 |; E7 R1 d& K* ]

8 W, _! Y5 w% T/ Z3.4 求值规则
" |9 W3 o- V+ W4 S  S" h- S" s$ H在多数情况下, Maple的求值规则设计为做用户期望的事情, 但要做到这一点很困难,因为不同的人在相同的情形下会有不同的期望. 在大多数情况下, 全局变量被完全求值, 局部变量被一层求值. 而由符号' '界定一个暂时不求值的表达式, 单步求值仅去掉引号, 不作计算, 这也是允许取消指定名字或清除变量的原因. 如下例:   
! ^( @& b- U7 O+ B( g9 p. \> x:=y;0 B( Z$ l+ w; F: A

, o  B/ J  E1 d> y:=z;
, P. ~. n2 d4 {6 Z4 g) {- i
7 h6 I) T3 m1 q4 x- }! H/ M% V> z:=3;# @# B" V* a! E- E) v  m9 C

8 E" W" p6 `: S; P> x;
) u' a4 w$ [& i3 G* A: F7 r: z7 Y/ ]
9 [" ?9 Y1 ~5 e" x5 T% E+ }6 X- q> y;& n8 y; L$ _" S3 p* G! t1 z

: x5 u3 Q( q0 g* q3 I( a> x:='x';
+ |5 p( |1 M  w$ }+ }
# o) {8 g1 j0 b6 r& T5 \> x;. }( R3 h9 g6 s! m5 C
9 J' g! `) R( D, j6 f
> y;$ U, q$ H: r! p9 _* g

1 K4 }4 d8 u+ o# M7 O+ a8 z对于不同的问题, Maple设计了不同的求值命令. 现分述如下:   ! R3 f4 f( F- z% @& [# F8 w
1) 对表达式求值! ?" x) H9 Z% u5 {1 z- h# j
命令格式: eval(e, x=a);  #求表达式e在x=a处的值' c% N3 ?& b+ L! `; c
             eval(e, eqns); #对方程或方程组eqns求值/ ?6 I2 [1 G$ e% ~3 b9 S7 H
             eval(e);      #表达式e求值到上面两层
9 X5 X) ]6 B; v; k1 J1 K             eval(x,n);    #给出求值名称的第n层求值, k; x/ H2 [4 w" J5 e
> p:=x^5+x^4+x^3+x^2+x+73;
; o4 I8 ^7 R, w: o0 r# O  M7 q
! [( U3 _( _& W) R1 E" z> eval(p,x=7);$ p. h( ?8 A; a) m+ }" Y' \

2 k  s4 E4 x" g/ t> P:=exp(y)+x*y+exp(x);" E1 _* X- b+ [! S( B' \
& p( ]* `3 U+ S
> eval(P,[x=2,y=3]);
  [4 U9 ^" ?+ B0 w$ r. b, O! z6 Q9 q ! C: S5 Y' c: R- k3 o7 |7 n
    当表达式在异常点处求值时, eval会给一个错误消息. 如下:   
: I: Q+ D) _$ f9 g2 t0 H> eval(sin(x)/x,x=0);4 t( p2 j, y1 D6 ]: [0 Z' l1 _2 A) T0 O
Error, numeric exception: division by zero# g7 `3 V6 a6 d: C& A" U. m
    下面再看使用eval进行全层求值或者对名称几层求值的示例:   1 D8 V% f5 M' D( a, S4 B2 g; H
> a:=b: b:=c: c:=x+1:
: o2 }  D7 q5 `% u6 |* |+ U> a;              #默认的全层递归求值, |1 i- W2 l( J& x* A: O) c) X

" d) y# S- R. F" o6 v> eval(a);        #强制全层递归求值" E  y% T( H% ^# Z: {+ C7 S; D
1 D3 Z4 z, i5 V" D6 r0 @- z
> eval(a,1);       #对a一层求值
8 w! d1 o. }: y; z
) `  J9 v+ a8 F4 B# |$ Y' y> eval(a,2);       #对a二层求值) W0 z) e9 _( _- @  L) F3 s

9 ?& A4 H8 r  w8 D8 x> eval(a,3);       #对a三层求值  `: W! b2 }2 H3 c1 H# z" g

' D. A5 d: W7 W* z/ W8 s3 S> eval(a,4);       #对a四层求值# Z$ F  o: N2 U  q- [8 _
$ }, d' q5 l" @* p% e; b" W  K
    2) 在代数数(或者函数)域求值
. N# l' x, ?2 y& E命令格式: evala(expr);       # 对表达式或者未求值函数求值
! q/ i* ^7 H: @: g- a             evala(expr,opts);   #求值时可加选项(opts)
2 s" Y! b7 ]* B6 G2 o所谓代数数(Algebraic number)就是整系数单变量多项式的根, 其范围比有理数大, 真包含于实数域, 也就是说任意实数都是整系数多项式的根(如 就不是任何整系数多项式的根). 另一方面, 代数数也不是都可以表示成为根式的, 如多项式 的根就不能表示成为根式的形式.
0 n. p8 z( H7 ~3 K3 p代数数的计算, 算法复杂, 而且相当费时. 在Maple中, 代数数用函数RootOf()来表示. 如 作为一个代数数, 可以表示为:   
' u9 R) U/ \5 Y> alpha:=RootOf(x^2-3,x);2 N* e* p: V' k% v% L% N* G7 }: V

; X! w! k  q% a! g0 V> simplify(alpha^2);( B- \+ \; h3 `; l. L

+ ]4 b6 Q& f  F( ~5 G( v6 p在Maple内部, 代数数 不再表示为根式, 而在化简时, 仅仅利用到 这样的事实. 这里, Maple用到一个内部变量_Z. 再看下面一个例子,其中alias是缩写的定义函数,而参数lenstra指lenstra椭圆曲线方法:6 ^% F9 W- y0 \0 N$ ~2 o
> alias(alpha=RootOf(x^2-2)):+ G1 r+ ^5 H$ p7 d
> evala(factor(x^2-2,alpha),lenstra);
% }, B& U: V3 Q7 b/ c7 e7 g; h2 e
% i' w" ]; o2 \; \( L> evala(quo(x^2-x+3,x-alpha,x,'r'));
- d4 D3 N1 F( ^1 ^7 t% c! z+ r
5 q- D2 i, p0 A& Y2 \" x> r;* y6 p# T# K6 X/ {# L! O$ \( G1 s6 X
; x" h( @( v6 o+ f: M& p. V
> simplify(%);) {- Q- s( _% s* J8 j) B
6 f; Z5 ~4 m" T( y* ]
3) 在复数域上符号求值
. s5 k9 J3 \, i; T* B: J操纵复数型表达式并将其分离给出expr的实部和虚部的函数为evalc, 命令格式为:* G$ c5 [. V9 ~: Y' y
evalc(expr);   
2 T& ?3 ^/ d* J5 q! E9 ]5 K: N. Hevalc假定所有变量表示数值, 且实数变量的函数是实数类型. 其输出规范形式为: expr1+I*expr2. 1 u6 D0 F0 b% V+ R8 l& a
> evalc(sin(6+8*I));& e' @3 y1 [7 n% D  j3 ^3 S. x

( ^4 v" ]* L0 d) h+ g. o> evalc(f(exp(alpha+x*I)));& a- H$ [1 n* P4 b# t

& P  [% P8 c( I- g7 g> evalc(abs(x+y*I)=cos(u(x)+I*v(y)));# B! ~2 T6 C. d/ Z
0 n% h' L8 c! T+ V8 T# o5 V& @
4) 使用浮点算法求值# T3 w" f7 x7 R) x" H* v4 j! |
浮点算法是数值计算的一种基本方法,在任何情况下均可以对表达式expr使用evalf命令计算精度为n的浮点数(n=Digits), 如果n缺省, 则取系统默认值, 命令格式为: evalf(expr, n);     $ F1 y" u! K& x
> evalf(Pi,50);    0 ~7 F0 Z8 G. [# ~

: r0 K# I7 Z) A4 u, ]; W) O4 I> evalf(sin(3+4*I));   
2 x; A6 q- a1 h
$ {7 f# P$ c" T& L> evalf(int(sin(x)/x,x=0..1),20);9 `0 v8 ]' k& K0 j0 S
' w0 K. [4 ^" h( L7 S
5) 对惰性函数求值5 }% @& i9 s, I2 X+ ^5 u- Y4 A7 E
把只用表达式表示而暂不求值的函数称为惰性函数, 除了第一个字母大写外, Maple中的惰性函数和活性函数的名字是相同的. 惰性函数调用的典型用法是预防对问题的符号求值, 这样可以节省对输入进行符号处理的时间, 而value函数强制对其求值. 对任意代数表达式f求值的命令格式为: value(f);   7 z* k' d4 K4 c! p
> F:=Int(exp(x),x);* X; ^- a5 @1 I* G9 W3 J
# l. V0 a- Y' L+ K
> value(%);/ U+ |4 F! l: _9 W

2 |' H5 U7 U. V2 T" d7 S> f:=Limit(sin(x)/x,x=0);( R) `2 E- i0 o+ q7 v; z( ^* v

; u4 y+ |. s" G+ V) Y+ O6 E/ H> value(%);& w* d  i* A5 O( {- N: ]
# o. Z& h' x- z4 l6 y: x& c
另外, 将惰性函数的大写字母改为小写字母亦即可求值. 如下例:   
( A5 s. r$ f" c. D) t> Limit(sin(x)/x,x=0)=limit(sin(x)/x,x=0);' F0 J( U; @; Q5 u7 J

; _% w: c3 b5 B7 T5 v! T  G4 数据结构
" {% j) C* B3 c& G1 Q6 @Maple中有许多内建的与FORTRAN、C或Pascal不同的数据结构. 主要的数据结构有序列(sequence)、列表(list)、集合(set)、代数数( algebraic number)、未求值或惰性函数调用、表(table)、级数(series)、串(string)、索引名(index)、关系(relation)、过程体(process)以及整数(integer)、分数(fraction)、浮点数(float)、复数(complex number)等数据结构, 而矩阵(matrix)在Maple中表示为阵列, 是一种特殊的表. 5 b) ~5 e3 E+ S5 |+ M
4.1 数据类型查询
# W  `8 w* Q4 ^. u3 I! [在Maple中, 用whattype指令来查询某个变量的数据类型或特定类型, 命令格式为:
; u# v  ~4 @6 r0 Y& b6 {whattype(expr)        # 查询expr的数据类型+ d! y7 F/ i% P: [+ H
type(expr, t)           # 查询expr是否为t类型, 若是则返回true, 否则返回false
) b5 x: }5 |% \0 u> whattype(12);
, q$ i' m# |) K& ?; Y; k5 }
/ o* ^! k+ C8 C> whattype(Pi);
) m& T5 U; B  U1 ^' h' O) _! G# K ( Y2 X& p1 E. n0 D! Y+ g; c
> type(1.1,fraction);9 P) I0 @- M4 g5 c8 y8 i( i# [
, H2 v/ A+ L2 j$ a1 Y* U9 e
> whattype(1.1);
! y) R% c* n9 K/ k0 l( t & o$ o8 A, u0 }
4.2 序列, 列表和集合0 n+ M2 ?# J7 U* n
4.2.1 序列
( p, @! N6 N9 ?7 b" v  v( p所谓序列(Sequence), 就是一组用逗号隔开的表达式列. 如:   * X' d( R, ^' d& V# z
> s:=1,4,9,16,25;1 H* T2 l* `* X; D) ?  B
1 t7 v6 o: n# |
> t:=sin,com,tan,cot;. y4 O3 H: q, F# `5 |

  C' T8 g$ o+ f一个序列也可以由若干个序列复合而成, 如:   4 g0 ~, Y+ @! q- ]: E7 j% G
> s:=1,(4,9,16),25;6 G( A( ^" j* ~6 @- |) U

3 t7 S* j- e* ~) r* f. Z9 @& E% c> s,s;+ }8 x5 R! \' T
; a% I* u' p2 `9 n, \9 Q# ?7 }7 w+ }
而符号NULL表示一个空序列. 序列有很多用途, 如构成列表、集合等. 事实上, 有些函数命令也是由序列构成. 例如:   
' A0 R/ z, d8 Q5 l+ X9 |# Y> max(s);, ?5 p) D1 K- h! z5 D
2 A2 C2 w6 @; t0 R
> min(s,0,s);
3 u! Y, F5 V3 K
+ I+ b2 t) O/ e( _; V+ |& g( C7 T值得注意的是, op和nops函数命令不适用于序列, 如op(s)或nops(s)都是错误的, 如果要使用op(s)或nops(s)前应先把序列s置于列表中. # x4 W. ]: ]5 P
> s:=1, 2, abc, x^2+1, `hi world`, Pi, x -> x^2, 1/2, 1;! R4 ?. m) |9 n3 _3 e
% e# B* |( e5 R
> op(s);0 x; H, I- S3 g) d5 |
Error, wrong number (or type) of parameters in function op* q  L6 \, b: {. v% Q9 Y3 r( H
> nops(s);
2 s" {1 d4 P# LError, wrong number (or type) of parameters in function nops" C; _, _$ R1 b% Q3 m
> op([s]);( i/ W+ L9 e, k1 w
; @/ C9 N2 y' i2 G8 g: k
> nops([stuff]);
4 h. k; q, F( U' D- a$ S) Z( E
" H5 z4 G/ o8 {! a' e  H3 `函数seq是最有用的生成序列的命令, 通常用于写出具有一定规律的序列的通项, 命令格式为:   / p) x" }2 t1 T# c1 ~/ v$ C  I3 n( @/ w
seq(f(i), i=m..n);  # 生成序列f(m), f(m+1), …, f(n) (m,n为任意有理数)
, P1 ~! Z$ a, m- k+ ~2 [" o! I. Hseq(f(i), i=expr);  # 生成一个f映射expr操作数的序列
& {8 G8 X# l0 Aseq(f(op(i,expr)), i=1..nops(expr));  # 生成nops(expr)个元素组成的序列) `# K/ z6 A( }2 T6 `; Y& ?! X3 ^: |6 j
> seq(i^2,i=1..10);
  u* h$ H7 [: {+ C) J- T3 }# z , l4 U' s/ m1 F. |
> seq(ithprime(i),i=1..20);: V4 f: {7 I$ H1 V7 a
  u1 L$ p$ w2 J3 b! ^  K
> seq(i^3,i=x+y+z);+ k) Z0 v% F3 A  L0 m- Q/ e

; C/ B) d. }( w; Q> seq(D(f),f=[sin,cos,tan,cot]);
4 }8 }0 j6 C5 Y; u" \ 1 d0 r. u1 \( }
> seq(f(op(i,x1+x2+x3+x4)),i=1..nops(x1+x2+x3+x4));
& N7 g0 G! M% s. ?: y* y # d$ @$ \# u, r6 S8 w9 ], m
获得一个序列中的特定元素选用操作符[  ], 如:   
* @. [8 f6 O7 N, B; ?5 N% @' T> seq(ithprime(i),i=1..20);& u4 o( d1 P: I# Z
5 L  f  A2 P1 W) J4 E
> %[6],%[17];
2 u$ A+ {% i/ L" n& j% u, h . o$ G% ?7 o7 t; i0 `1 E" a
4.2.2 列表3 _5 l0 |& U) e( Y' j: d* R9 E
列表(list), 就是把对象(元素)放在一起的一种数据结构, 一般地, 用方括号[  ]表示列表. 如下例:   : [0 a0 L6 \. Y# _: k1 W
> l:=[x,1,1-z,x];  C, ~, Z5 O' f6 o6 h( c6 o$ r
3 ?$ r" L4 J5 A
> whattype(%);
& P- x- }( }% P3 ?1 J* Y+ N + z. ~7 t5 y& `- n+ e* t  L
空列表定义为[ ]. % _; H! |) J5 r( O  l$ p9 f2 K
但下述两个列表是不一样的, 因为对于列表而言, 次序是重要的:   
- \5 F0 h3 h3 N" e- b> L:=[1,2,3,4];
2 p1 m. m" _' z! G2 o
5 E" y6 g( Q6 X9 \5 m, I( ^# _7 Z> M:=[2,3,4,1];
' _% W* I1 v/ J  Q$ o+ ]0 b' s & S4 a% ^# P0 U
4.2.3 集合
- h: O! v1 [& r3 r$ |) a6 }* v2 A. A集合(set)也是把对象(元素)放在一起的数据结构, 与列表不同的是集合中不可以有相同的元素(如果有, Maple也会自动将其当作同一个元素), 另外, 集合中的元素不管次序. 一般地, 用花括号表示集合. + i3 \, q9 {/ r7 d$ y0 s
> s:={x,1,1-z,x};) J3 X7 B7 V# Y6 R

$ r# y5 z( t2 T4 s  Q> whattype(%);
$ m, D/ b5 J! U9 j
* K! q/ Q# j' P$ A空集定义为{ }.
  z7 _: Y& v' |0 p* A函数nop返回列表或集合的元素数, 而op则可返回其第I个元素.
3 p0 z; w( _/ K' `8 Q  }: |. N> op(1,s);
8 q  R9 ^" e+ C* [ , P4 S/ C- T7 q+ U. Y
> s[1];, J, R/ H) N* L, H
  l& Y! Z3 P0 ?; X0 z' S) W6 C
> op(1..3,s);
: E+ ]) y( N( M/ R
0 g+ g. O1 M2 @7 e> s[1..3];
; M0 v: }3 e( A7 y4 h ( _6 f7 M& E% A1 V" X) ?
函数member可以判定元素是否属于一个列表或集合, 如果属于, 返回true, 否则返回false.
& I/ g. a/ C! N3 i5 m% D6 T> member(1+x,s);) ?- r2 m! M1 I- L, V

: j2 r. X5 B- w* D9 `可以通过下述方法在列表中增减元素:   
4 Z" S# h  U0 r1 V. c6 {' m2 s> t:=[op(s),x];" c' ]' o+ Q6 g( @

) b9 z9 z0 l" f& i' A5 l' I" U( M2 h> u:=[s[1..5],s[7..nops(s)]];, L9 h$ q3 n7 f! s( d

6 _: ]8 I7 ^8 g* UMaple中集合的基本运算有交(intersect)、并(union)、差(minus):   5 n' q0 d7 k% k) \1 t' S! p
> A:={seq(i^3,i=1..10)};B:={seq(i^2,i=1..10)};) H2 u' c$ S! ?6 O5 J
$ _/ M( Q5 _5 Q$ I! h. i

5 C$ W1 p. A. i% F- t> A intersect B; ) A- f: S. W9 F. b
' v5 Q+ {7 ?9 D+ K* n! Y) {
> A union B; 5 \& X, R3 s1 W# G9 F! j
% l. y4 ~2 e0 M; D- d2 o- o6 M
> A minus B;$ o3 m% d+ {/ B; c6 x

& o) V' y9 k" I4.3 数组和表1 F' H3 \, n7 `5 ?
在Maple中, 数组(array)由命令array产生, 其下标变量(index)可以自由指定. 下标由1开始的一维数组称为向量(vector), 二维以上的数组称为矩阵(matrix). 数组的元素按顺序排列, 任意存取一数组的元素要比列表或序列快的多. 区分一个数据结构是数组还是列表要用“type”命令.   ~, H/ m6 b8 b: I7 ~0 \: Q. U/ m: Y
    表(table)在建立时使用圆括号, 变量能对一个表赋值, 但一个在存取在算子中的未赋值变量会被自动地假定是表, 表的索引可以成为任意Maple表达式. 表中元素的次序不是固定的.
5 z3 H3 a! b- w0 ]3 U! ^7 L# |> A:=array(1..4);, v( j- @$ x# `" s: J' S+ i5 Z

- u9 @/ u$ P! D1 Y; g4 {" w> for i from 1 to 4 do A[i]:=i: od:# v5 a/ C* i1 V& I# |
> eval(A);
7 R8 G0 e! F( h1 \  |3 q
/ W, P. ^+ ^# u& u> type(A,array);1 t6 d2 i8 {6 o9 s9 S0 g+ o( Q; H8 x0 C* m

; G5 F2 G- S& T3 P3 F> type(A,list);" E/ u/ V' e6 r% x- v  `

2 G. p' i9 }0 k; {7 V9 _: @: A> T:=table();- X& T/ n5 C& Y! H# s4 u1 F

) ~% s+ i8 K# B. n: l, r' L1 `> T[1]:= 1;1 v# u" A7 K6 q  |( Q

7 P4 }+ E8 s; Q2 ]  A, _> T[5]:= 5;; |( e" l& f1 ]% u0 I" G  d  r
2 j( d1 b& N# j3 W; d- h
> T[3]:= 3;
8 J- U& J6 F7 D4 \& k
/ Y% O, e0 {7 l$ d0 g6 [5 ?> T[sam]:=sally;, b* O3 M1 B/ [' ^
! x  t) l+ L7 g7 c3 {/ q
> T[Pi]:=exp(1);" V9 V: D+ T. ?: A6 m" o
' A0 ~5 p, `& l* H+ O$ F& X
> x:='x';- e& E; L/ t# K7 |+ z0 H- ]: ^, ]
% i- f) M+ H$ @6 K3 L, u0 ^" H
> T[(1+x+x^3)*sin(x)] := 0;
. v8 E8 i& z2 ]; M9 f' y. H
, j- a/ A4 ?/ o+ J3 s> eval(T);
7 ]/ X% x7 c  `  k- k2 b* h
" \) L! q3 m( G> T[3]:='T[3]';* |6 z) i7 @* [3 U' _: P
3 b6 T4 Y6 w" U! L/ \
> eval(T);
: X9 Z5 l5 |- C+ ~
1 r9 R, D9 a  D$ I. W& g  |  X4.4 其他数据结构3 M: b7 x/ _6 j0 j
串在Maple中是很重要的, 他们主要用于取名字和显示信息. 一个Maple的串可以作为变量名, 它们中的大多数是简单的、不需要加引号的串, 但是如果变量名中包含/. 例如“diff/T”则必须把变量名用引号括起来. - P$ e; W5 ?1 I) A1 H
索引名是像Database[1,2,drawer]或A[3]这样的对象, 在使用索引前不需要直接建立表, 如果不得不做, Maple会自动建立表. 索引名通常被用于矩阵和向量. 为了保证Maple建立表的正确次序, 建议在赋值前直接建立. 3 T; w7 x4 C# p+ m) P( d; Q. w
> x:=T[3];/ |  |1 _: T0 g

  D( `/ v/ A' g6 o> eval(T);
3 a: T' R1 f  g2 T) @, N
! ^! k! `2 p7 d2 D5 ^4 D8 k- n/ v> T[5]:=y;
8 l7 B3 G: E3 m0 u( ]& X
0 ^  ~+ v7 ^$ B: e, b> eval(T);/ \4 r$ w8 w0 q0 h; C9 |9 t

: G  R* a, k- j1 J# r由此可见, Maple并不直接建立T的表, 直到给T[5]赋了值.       n% Z7 ~* O8 c) ^2 q
数值数据结构(整数、分数、有理数、浮点数、硬件浮点数和复数等)在它们的使用中是大量透明的. 浮点数是有传染性的, 这意味着如果数值结构中有一个是浮点数, 则整个结构自动转换为浮点数. , ^% Y4 q) H) [# K; }! p* g
4.5 数据类型转换和合并, m" N7 J( y+ b# F% D  Q0 i0 Q7 O1 ~
convert是一个功能强大的类型转换函数, 它可以实现列表和数组的类型转换:   
+ E/ S3 v: }* X, x' |# f5 ^) e5 q> L:=[1,2,3,4];
+ z1 y, I* ^8 A1 H, L( H7 I , j' m9 @& W) Z- i  h# H) A
> type(L,list);! ]9 l% K7 O1 z: {5 f
0 R0 V0 o' B3 @7 j+ T
> A:=convert(L,array);
1 E/ O0 ^. z( A# v$ d3 Q9 D
3 M% ?  S- q( y> type(A,list);" q, {+ u; \) ^% S

# Y, C8 ]; J$ B0 _> type(A,array);( ?( U! I: \7 a/ `" H) x2 I. F# t

( |4 y4 _$ I- V4 I/ g另一个有用的函数zip则可把两个列表或向量合并:   . L) {5 ^2 f4 [) u+ L' X& }: I
>L:=[seq(i,i=1..10)];
. M/ Y/ L3 j4 p7 V- q) R3 d9 K
0 u" W4 h/ Q3 m4 e5 \> Sqr:=(x)->x^2;& o1 w4 m$ L$ [& g6 ~0 ^( q
# p& l2 x1 W. E5 O
> M:=map(sqr,L);& `1 Y. j% X3 P
! S, w3 i% ^, z: o. I
> LM:=zip((x,y)->[x,y],L,M);
& }3 r9 w, M! z
6 k9 w0 T- Y, `+ u> map(op,LM);
" m1 P# ^8 M) p! p' x- O' H . Z" z7 Y& q. ]. k1 b
5 Maple高级输入与输出操作/ ?. u4 D: W9 k# d. k# q# f7 t
Maple提供了良好的接口来编辑与计算数学式. 许多时候, 我们可能需要把Maple的运算结果输出到一个文件中, 或者在一个文本编辑器里先编好一个较大的Maple程序, 再将它加载到Maple的环境里.
+ T. V3 [7 D2 k4 F' y5.1 写入文件7 ^  N, X' ~* y% _4 n
5.1.1 将数值数据写入到一个文件
/ s" y4 D8 |, O. b+ Z如果Maple的计算结果是一长串的数值串行或数组, 而想把它写到一个文件时, 用writedata命令. 6 k9 p. P' T1 d, `) U9 l- N  {
若Maple的计算结果data为集合、矩阵、列表、向量等形式时, 将其写入名为filename的文件时命令格式为: writedata("filename", data);$ S) e( c( O- V7 v9 [: [+ |0 \
> with(linalg):
  z$ ^9 j+ n, K- a  j> M:=matrix(3,3,[1,2,3,4,5,6,7,8,9]);
( i9 Y/ i- ]; M' @ ) e( I9 Q# `( H3 S6 A6 X  e8 S4 P
> writedata("e:\\filename.txt",M);" h5 V( p% H6 Q# `
而将结果附加在一个已存在的文件后时,使用命令: writedata[APPEND]("filename", data);
1 j1 w, s: z5 h) ]( M) `! V" n3 p> W:=matrix(2,2,[1,2,3,4]);
* T  Y! P! c+ R- t* `4 v" F: g ' R( o& P7 `, \' O/ D, d5 r; E& ^" }
> writedata[APPEND]("e:\\filename.txt",W);
; @; Q' L+ P: n, v5 Q8 k/ O1 n需要注意的是, 这里的APPEND是必需的, 否则W结果将会覆盖M结果.
( u3 z1 S1 i3 j' P另外, 若想将结果显示在屏幕上时, 用命令: writedata('terminal', data);9 F; X2 E. X/ r* ?% w/ E
> writedata[APPEND]("e:\\filename.txt",W);
7 j" E7 V3 p  U: n% W  |7 m) H: s- G> writedata('terminal',M);0 l9 s7 ]- F5 T( O
1                   2                   3           0 C2 U' U% q5 F6 h. C# g0 M
4                   5                   6           
2 T, k# p# t8 C: q* r% {, O" h' c2 k7                   8                   9    . T0 l& `& T- T* r: I. ]$ C6 e* }
5.1.2 将Maple语句写入一个文件
9 [8 M1 W  ]5 o7 c  n' p4 s如果所要写入文件的是表达式、函数的定义或者是一个完整的程序, 则使用命令save, 写入一个或多个语句的命令格式分别如下:
; Q) V$ ^3 b+ r6 isave name, "filename";
5 I" E) [% a. F/ ]save name1, name2, …, "filename";
: V( a9 V0 v$ X1 R! }若filename的扩展名为.m, 则Maple会以内定的格式储存, 若扩展名为.txt, 则以纯文本文件储存. 以内定的格式储存的文件作纯文本编辑器无法读取, 但在大多数情况下, 它会比纯文本文件的加载速度更快, 且文件容量小.
6 e6 P( p, H5 l; j  Y# W> myfunc:=(k,n)->sum(x^k/k!,x=1..n);, p) M* a, k: M2 [# N, N

2 g" G" ?: t) O2 s) H> myresult:=myfunc(6,8);; y& {0 P' |% m/ n5 f7 ^& e
% ?# S6 `# D7 M1 d# Y
> save myfunc,myresult,"e:\\test.m";( |8 d2 r/ Q  I  W$ `; i# d
调用已存m文件用命令read. 试看下述实验:
5 O9 H' j4 M0 C$ B' P0 s> restart:
  |+ L* e: d" A9 c1 ?> myfunc(6,8);
$ H% Z1 ~5 F- s5 g; X! Z
- Q4 F+ ~0 S, K, b> read "e:\\test.m";6 `$ V: g, U/ s- l4 F
> myfunc(6,8);8 Y9 r7 a+ X' S3 T/ B4 h( D

9 \+ Y! _4 F5 s( M& {( a0 n> myresult;6 W/ V5 ]/ ?( k# l: A
- T4 ]: ?" F% Y6 C! @/ u
    而存为txt文件时则将整个语句存为一个文件:2 W1 Q* l- ^# P
> save myfunc,myresult,"e:\\test.txt";
% ^$ V9 a7 V$ o  E( }9 u> restart: read"e:\\test.txt";, s: L2 `9 V4 U; C
+ \( c, _4 @- `$ R6 I
4 A4 ~) ]2 y2 o  Y' }1 Q$ q9 m/ m
5.2 读取文件
$ a) g- A- H, p% O) t1 A+ T0 n' P在Maple里最常用的两个读取文件的命令, 一个是读取数值数据, 另一个是是读取Maple的指令.
- i8 }/ s! ?) e  x, I( K5.2.1 读取数值数据
/ B; r2 i* [% F& O- ^4 S/ d如果想把大量的数据导入Maple里进行进一步的运算或者要运用大量的实验数据在Maple环境绘图时, 可以用readdata( )命令完成.
0 R  A2 R% J4 W; a1 n: m从filename文件里读取n行数据时使用命令: readdata("filename",n);
" q' l% c; G2 j$ z以指定的格式读取数据时使用命令: readdata("filename",[tyep1,type2,…]);
+ y/ U% q/ }2 O> readdata("e:\\filename.txt",3);
' M, k# I9 `1 C) x, Q8 Y! s3 ~$ t
$ z7 i/ U7 E+ l& M' g    读取filename的前三列, 第一列为整数形式, 第二、三列为浮点数形式:
0 Q, q" q7 ^) z> readdata("e:\\filename.txt",[integer,float,float]);, T9 c5 e& A' D# J

, y  U6 H. s/ K9 H/ j' I! o下面再看一个运用大量的实验数据在Maple环境绘图的实验:
4 T0 @& G3 y; \8 N+ S> mypts:=[seq([x/1000,cos(x^2/100000)],x=1..1000)]:7 h2 U; ^* c0 n+ r! F# l$ b7 b! V3 s
> writedata("e:\\data.txt",evalf(mypts));' K8 n& }$ G: z0 x/ W5 P) W+ {# u
> dots:=readdata("e:\\data.txt",100):/ V& X  m9 F: n
> nops(dots);6 E+ \- `; D, Y7 W: k
6 m+ @' x2 c* c* R# x9 _) u, L0 A
> dots[1..4];! |' B+ F. ]+ u" ]  ~0 M
9 B* W) m$ H, x2 e. |5 a
> plot(dots,style=line);
+ y9 P' L8 W3 A# n6 T1 I" N7 B
8 ^4 z; V) w$ H+ S1 P: N8 w5.2.2 读取Maple的指令
" `7 t, L% V! J' A' P在编写程序时, 在普通软件中先编好程序再将其读入Maple环境中常常比直接在Maple中编写更为方便. 如果要将程序代码或Maple指令加载用read命令:. f. y) }& h& R) h2 @
read "filename";; H& d' j- u2 i* |4 w% h1 I
如下例:( D$ p# N, l% R! J" o
> reatart:
  k  z, q$ C" Y* _6 v1 J3 f> myfunc:=(a::list)->add(i,i=a);
* L$ m5 J# y! B& D
  ^; }' W9 e4 w2 n8 @& |9 c> avg:=(a::list)->myfunc(a)/nops(a);+ ~! E# E  l5 Z, `( P2 E

. o/ @1 t0 m% J' ^- k3 |> save myfunc,avg,"e:\\function.m";# |1 a& c9 \% |2 P0 Q+ I& j
> restart:
3 r# W5 b3 l5 S! G  s1 z3 W> read "e:\\function.m";( F- O3 _8 H5 M# M6 i
> myfunc([1,2,3,4,5,6,7,8,9]);9 I" |6 s4 x9 H! f

9 y, b% f- t8 @; E' e8 A& j7 V> avg([1,2,3,4,5,6,7,8,9]);- k) _0 W, |& k% I3 G& P3 V4 p0 z% ^2 S
) _# v2 B5 I; V! o, w
5.3 与其它程序语言的连接
) U3 o9 A; n4 A. f5.3.1 转换成FORTRAN或C语言5 K: D) x. b* U
调用codegen程序包中的fortran命令可以把Maple的结果转换成FORTRAN语言:+ K, _# w6 j# {
> with(codegen,fortran):9 R, Z* D3 Z8 O
f:= 1-2*x+3*x^2-2*x^3+x^4;( D6 y4 l) S. O9 L( g; J1 e

) D, I2 z$ U$ J( E( k5 j% {) L. d, }> fortran(%);
. X6 S0 j: O, x& C6 M) l) Y      t0 = 1-2*x+3*x**2-2*x**3+x**4% W; V, A' u8 T3 Y; P9 O: ~. C
> fortran(f,optimized);
5 }& \: g9 n; m      t2 = x**2
* B0 N* @5 O, i. J      t6 = t2**2# U$ k9 r" z' d/ I
      t7 = 1-2*x+3*t2-2*t2*x+t6' x4 Q$ F4 n7 ~& V9 K
> fortran(convert(f,horner,x));
6 X5 o# e( z/ H2 Y; w9 I: @      t0 = 1+(-2+(3+(-2+x)*x)*x)*x' |9 p+ q! l$ s. r2 t
而codegen程序包中的C命令可以把Maple结果转换成C语言格式:# L) V/ ~" W0 F, V8 y
> with(codegen,C):! M2 J0 F2 ^4 F! D- X0 P& o
f:=1-x/2+3*x^2-x^3+x^4;
9 y+ D; l* @$ @  H4 \: \) W9 H
: t( Q) R1 ?# _6 _# t% s> C(f);
$ m) H+ @( U# H, X      t0 = 1.0-x/2.0+3.0*x*x-x*x*x+x*x*x*x;& r- q8 U' N) Q/ V8 T
> C(f,optimized);; {4 A5 _! l0 Q, U, t8 f
      t2 = x*x;
0 J9 ^& Y, W0 A3 V      t5 = t2*t2;9 w) O" S- N: ]+ a+ l% a
      t6 = 1.0-x/2.0+3.0*t2-t2*x+t5;7 g) s0 Z2 P! Z! L  M) [+ H6 m
optimized命令表示要对转换的表达式进行优化, 如果不加此可选参数, 则直接对表达式进行一一对应的转换.% A2 C7 B* d" b( h: ?3 o  }
5.3.2 生成LATEX) Z/ ?9 J' I  W/ C' U8 V
Maple可以把它的表达式转换成LATEX, 使用latex命令即可:& \! U) u. ^/ w# g& k
> latex(x^2+y^2=z^2);" p, E# p. r& X
{x}^{2}+{y}^{2}={z}^{2}# y2 c; i3 N1 G- x. j
    还可以将转换结果存为一个文件(LatexFile):
% }4 J% f" ~! c' {6 J> latex(x^2 + y^2 = z^2, LatexFile);
. v* d0 y  Z2 B) I) x9 G- U- {9 w) Z    再如下例:
1 g- s0 \0 u1 u( c! G0 I( }8 n1 K> latex(Int(1/(x^2+1),x)=int(1/(x^2+1),x));3 j0 E# [* R$ o% r7 ^! |) I
\int \! \left( {x}^{2}+1 \right) ^{-1}{dx}=\arctan\left( x \right)
  d; m" k3 W9 A/ {# W  C+ c4 W. B+ T/ @3 F+ c
zan
已有 1 人评分体力 收起 理由
darker50 + 2 用word发不是很好吗?呵呵!

总评分: 体力 + 2   查看全部评分

转播转播0 分享淘帖0 分享分享0 收藏收藏1 支持支持0 反对反对0 微信微信
darker50        

107

主题

45

听众

1万

积分

  • TA的每日心情
    开心
    2015-4-9 15:42
  • 签到天数: 47 天

    [LV.5]常住居民I

    自我介绍
    开朗,爱各种娱乐的不老男生就是我了,喜欢数学建模,喜欢那种帮助别人的感觉。

    社区QQ达人 助人为乐奖 新人进步奖

    回复

    使用道具 举报

    33

    主题

    10

    听众

    1691

    积分

    升级  69.1%

  • TA的每日心情
    开心
    2014-7-8 08:29
  • 签到天数: 201 天

    [LV.7]常住居民III

    发帖功臣 新人进步奖

    群组PLC和单片机

    群组2012第三期美赛培训

    群组MCM优秀论文解析专题

    群组沈阳理工应用技术学院

    群组学术交流B

    回复

    使用道具 举报

    33

    主题

    10

    听众

    1691

    积分

    升级  69.1%

  • TA的每日心情
    开心
    2014-7-8 08:29
  • 签到天数: 201 天

    [LV.7]常住居民III

    发帖功臣 新人进步奖

    群组PLC和单片机

    群组2012第三期美赛培训

    群组MCM优秀论文解析专题

    群组沈阳理工应用技术学院

    群组学术交流B

    回复

    使用道具 举报

    46

    主题

    3

    听众

    1967

    积分

    升级  96.7%

  • TA的每日心情

    2014-4-15 00:06
  • 签到天数: 5 天

    [LV.2]偶尔看看I

    社区QQ达人 新人进步奖

    群组数学建模

    群组数学趣味、游戏、IQ等

    群组LINGO

    听说女人如衣服,兄弟如手足。回想起来,我竟然七手八脚的裸奔了20年!, Z3 q- H; B  X) T0 f: u
    2 C' }/ ]9 p4 E+ T

    * ?( C3 l1 ]: n
    回复

    使用道具 举报

    0

    主题

    2

    听众

    19

    积分

    升级  14.74%

    该用户从未签到

    新人进步奖

    回复

    使用道具 举报

    0

    主题

    4

    听众

    181

    积分

    升级  40.5%

  • TA的每日心情
    开心
    2012-10-11 12:35
  • 签到天数: 51 天

    [LV.5]常住居民I

    群组学术交流A

    群组学术交流B

    回复

    使用道具 举报

    0

    主题

    13

    听众

    27

    积分

    升级  23.16%

  • TA的每日心情
    奋斗
    2015-9-29 17:01
  • 签到天数: 10 天

    [LV.3]偶尔看看II

    社区QQ达人

    群组国赛讨论

    回复

    使用道具 举报

    您需要登录后才可以回帖 登录 | 注册地址

    qq
    收缩
    • 电话咨询

    • 04714969085
    fastpost

    关于我们| 联系我们| 诚征英才| 对外合作| 产品服务| QQ

    手机版|Archiver| |繁體中文 手机客户端  

    蒙公网安备 15010502000194号

    Powered by Discuz! X2.5   © 2001-2013 数学建模网-数学中国 ( 蒙ICP备14002410号-3 蒙BBS备-0002号 )     论坛法律顾问:王兆丰

    GMT+8, 2025-11-3 05:34 , Processed in 0.754280 second(s), 94 queries .

    回顶部