Cách viết chương trình con trong Pascal
Chương trình con là một chương trình độc lập, xử lý một công việc nhất định nào đó trong chương trình chính, nó có chỉ có thể thực hiện được công việc đã được lập trình khi ở chương trình chính có lời gọi đến nó. Trong khi lập trình giải 1 bài toán, đôi khi chúng ta gặp phải những đoạn chương trình lặp đi lặp lại nhiều lần ở những phần xử lý khác nhau, để cho tiện lợi và không mất công, chúng ta định nghĩa 1 chương trình con với công việc được lập trình sẵn, khi cần thiết chỉ việc gọi chương trình con ra để làm việc mà không cần phải lập trình lại phần đã làm ở trên. Việc sử dụng chương trình con vô cùng tiện lợi và đảm bảo tính chặt chẽ của chương trình, thậm chí nhiều khi nếu không sử dụng chương trình con thì bài toán sẽ trở nên vô cùng rắc rối, và việc gỡ lỗi trong chương trình trở nên rất nan giải. Pascal cung cấp cho chúng ta 2 loại chương trình con là Procedure ( Thủ tục ) và Function ( Hàm ). Đây là hai chương trình con sẽ theo các bạn trong suốt quá trình học. Đây chính là cơ sở để khi các bạn học lên các ngôn ngữ lập trình 32 bit, các bạn sẽ không bị bỡ ngỡ khi lập trình với lớp ( Class ) và Thư viện ( Library ). Hay nói một cách ngắn gọn, đây chính là phần quan trọng nhất trong kỹ thuật lập trình Pascal. Phần này tương đối phức tạp, nên bạn cố gắng tập trung để phân biệt, khi nào nên dùng Thủ thục, khi nào nên dùng Hàm, và các khái niệm liên quan khi tham chiếu các thành phần của các chương trình con. Vị trí chương trình conNhắc lại cấu trúc của một chương trình Pascal Program { tên của chương trình } Uses { khai báo các thư viện } Const { khai báo các hằng toàn cục } Var { khai báo các biến toàn cục } { khai báo hàm / thủ tục (nếu cần) } Begin { bắt đầu khối chương trình chính } ... End. { kết thúc khối chương trình chính } Như vậy phần khai báo chương trình con phía sau phần khai báo biến toàn cục (sau từ khoá Var) và trước phần thân của chương trình chính (Trước Begin của chương trình chính) Phân biệt cách sử dụng hàm và thủ tụcHàm khác thủ tục ở chỗ hàm trả về một giá trị cho lệnh gọi thông qua tên hàm còn thủ tục thì không.
Chú ý: Nếu một công việc có thể làm bằng hàm thì chắc chắn sẽ làm được bằng thủ tục {tuy nhiên sẽ phức tạp hơn khi dùng hàm} nhưng một chương trình làm bằng thủ tục thì chưa chắc ta đã làm được bằng hàm.
CHƯƠNG TRÌNH CON- THỦ TỤC VÀ HÀM
Chương trình con là một chương trình nằm bên trong một chương trình khác. Chương trình con có 2 loại: Thủ tục (Procedure) và hàm (Function):
Chương trình con được dùng rộng rãi khi xây dựng các chương trình lớn nhằm làm cho chương trình dễ theo dõi, dễ sửa chữa, có thể phân mảnh chương trình cho nhiều người làm. Một đặc điểm nổi bật của chương trình con là nó có tính đệ quy nhờ thế mà nhiều bài toán được giải quyết dễ dàng. CẤU TRÚC CHUNG CỦA MỘT CHƯƠNG TRÌNH CÓ SỬ DỤNG CHƯƠNG TRÌNH CON: PROGRAM Tên_chương_trình; USES CRT; CONST ............; TYPE ............; VAR ............; PROCEDURE THUTUC[(Các tham số)]; [Khai báo Const, Type, Var] BEGIN .............. END; FUNCTION HAM[(Các tham số)]: [Khai báo Const, Type, Var] BEGIN .............. HAM:= END; BEGIN {Chương trình chính} ................... THUTUC[(...)]; ................... A:= HAM[(...)]; ................... END. Chú ý: Trong quá trình xây dựng CHƯƠNG TRÌNH CON, khi nào thì nên dùng thủ tục/hàm?
( ví dụ n!, tìm điểm đối xứng) Ví dụ 1.1: Viết CHƯƠNG TRÌNH CON để tính n! = 1.2...n. Function GiaiThua(n:integer):integer; Var P, i:integer; Begin P:=1; For i:=1 To n Do P:=P*i; GiaiThua:=P; End; Ví dụ 1.2: Viết chương trình con để tìm điểm đối xứng của điểm (x,y) qua gốc tọa độ. Procedure DoiXung(x,y:Integer; Var xx,yy:Integer); Begin xx:=-x; yy:=-y; End; CHÚ Ý: Trong 2 ví dụ trên: n, x, y được gọi là tham trị (không có từ khóa var đứng trước) vì sau khi ra khỏi chương trình con giá trị của nó không bị thay đổi. xx, yy được gọi là tham biến (có từ khóa var đứng trước) vì sau khi ra khỏi chương trình con giá trị của nó bị thay đổi.
Các chương trình con có thể không cần tham số mà chỉ có các biến riêng (biến cục bộ). Trong trường hợp cần nhận các giá trị mà chương trình mẹ truyền cho thì chương trình con cần phải có các tham số. Tham số thực là những giá trị lưu trữ trong các biến toàn cục của chương trình mẹ, được truyền cho các thủ tục hoặc hàm thông qua lời gọi tên của chúng. Tham số được khai báo ngay sau tên chương trình con được gọi là tham số hình thức. Tham số hình thức gồm: Tham biến là những giá trị mà chương trình con nhận từ chương trình mẹ, các giá trị này có thể biến đổi trong chương trình con và khi chương trình con kết thúc các giá trị này được trả về cho tham số thực. Cách khai báo tham biến: Tên chương trình con (Var tên tham biến: kiểu dữ liệu); Tham trị là những tham số truyền vào cho chương trình con xử lý nhưng khi quay về chương trình mẹ vẫn phải giữ nguyên giá trị ban đầu. Tên chương trình con (tên tham trị: kiểu dữ liệu);
Khi tham số hình thức trong chương trình con là tham biến thì tham số thực trong chương trình mẹ phải là biến chứ không thể là hằng. Trong mọi trường hợp cả hai tham số thực và tham số hình thức đều phải cùng kiểu dữ liệu…(các tham biến khi ra khỏi chương trình con giá trị thay đổi). Khi tham số hình thức là tham trị thì tham số thực phải là một giá trị.
Chú ý: Trong một chương trình con, nếu biến toàn cục trùng tên với biến địa phương thì biến địa phương được ưu tiên hơn. Ví dụ 1.3: Program KhaoSatBien; Var a,b: Integer; {biến toàn cục} Procedure ThuBien; Var a: Integer; {biến địa phương} Begin a:=10; Writeln(‘A=’,a,’B=’,b); End; Begin a:=50; b:=200; ThuBien; {A=10 B=200} Writeln(‘A=’,a,’B=’,b); {A=50 B=200} End.
Thông thường lời gọi một chương trình con chỉ được thực hiện khi chương trình con đó đã được thiết kế hoàn chỉnh. Tuy nhiên, Pascal còn cho phép một chương trình con ngay khi trong quá trình xây dựng lại có thể gọi tới chính nó, tính chất này được gọi là “Đệ quy của chương trình con”.
Một chương trình mẹ có nhiều chương trình con trực thuộc, bên trong mỗi chương trình con lại có thể có các chương trình con riêng. Khi thiết kế, mỗi chương trình con phải là một khối riêng biệt hoặc có thể có các lệnh nhảy Goto từ chương trình con này tới chương trình con khác.
Lời gọi chương trình con có thể đặt bất kỳ chỗ nào trong chương trình mẹ. Nếu chương trình con là một thủ tục thì lời gọi chương trình con có thể tạo nên một câu lệnh, ví dụ: Readln; Nếu chương trình con là hàm thì tên hàm không thể tạo nên một câu lệnh, vì vậy tên hàm phải nằm trong một biểu thức hay trong một thủ tục nào đó. Ví dụ, ta không thể viết: Sqrt(9); gọi hàm như sau là hợp lệ: a:=sqrt(9)+5;
Các chương trình con cùng cấp có thể gọi tới nhau và truyền tham số cho nhau. Nguyên tắc gọi là: những chương trình con xây dựng sau có thể gọi tới các chương trình con đã xây dựng trước nó, đồng thời các chương trình con cấp dưới cũng có thể gọi tới các chương trình con cấp trên nếu chúng cùng một gốc. Các chương trình con xây dựng trước muốn gọi tới các chương trình con xây dựng sau thì phải có chỉ báo forward. Xét một số ví dụ sau: Ví dụ 1.4 Program Goi_CTC; Type dayso=array[1..60] of byte; S1:=string[30]; Var a:s1; b:dayso; i,j,n:byte; Procedure nhapso(m:byte; var c:dayso); Begin For i:=1 to m do begin Write(‘c[‘,i.’]=’); readln(c[i]); End; End; Function tinhtong(m:byte; var d:dayso):real; Var tong:real; Begin tong:=0; For i:=1 to m do tong:=tong+d[i]; Tinhtong:=tong; End; Procedure Inkq(k:byte; e: dayso); Begin Write(‘tong cac ptu =’,tinhtong(k,e):8:0); {chương trình con gọi một chương trình con cùng cấp} Readln; End; BEGIN Write(‘nhap so ptu n’); readln(n); Nhapso(n,b); Inkq(n,b); End. Nếu hàm tinhtong xây dựng sau thủ tục Inkq, thì phải có chỉ báo forward. Thêm dòng: Function tinhtong(m:byte; var d:dayso):real; forward; trước khi xây dựng các chương trình con. Ví dụ 1.5 Program Goi_CTC; Type dayso=array[1..60] of byte; S1:=string[30]; Var a:s1; b:dayso; i,j,n:byte; Procedure nhapso(m:byte; var c:dayso); Begin … End; Function tinhtong(m:byte; var d:dayso):real; Var tong:real; Begin … End; Procedure xuly(j:byte;ds:dayso); Procedure Inkq(k:byte;e:dayso); Var i:byte; Begin Writeln(‘tong cac phan tu mang=’,tinhtong(k,e):8:0; Writeln (‘day so sap xep giam dan’); For i:=1 to k do write(e[i],’ ‘); Readln; End; {ket thuc thu tuc Inkq} Procedure sapxep(m:byte;ds:dayso); Var p,q:byte; tg:byte; Begin For p:=1 to m-1 do For q:=p+1 to m do If(d[p] Begin Tg:=d[p]; d[p]:=d[q]; d[q]:=tg; end; inkq(m,d); {goi den chuong trinh con cùng cấp} end; {ket thuc thu tuc sap xep} Begin {than thu tuc Xuly} Write(‘thu tuc xu ly dung de sap xep va in ket qua} Sapxep(j,ds); End; BEGIN Write(‘nhap so phan tu’); readln(n); Nhapso(n,b); Xuly(n,b); END. Bài tập: Tính Cnk=n!k!(n−k)! size 12{C rSub { size 8{n} } rSup { size 8{k} } = { {n!} over {k! \( n - k \) !} } } {} (có sử dụng chương trình con) |