Giáo trình Lập trình ứng dụng: Phần 2 - CĐ Kỹ Thuật Cao Thắng

72 15 0
Giáo trình Lập trình ứng dụng: Phần 2 - CĐ Kỹ Thuật Cao Thắng

Đang tải... (xem toàn văn)

Tài liệu hạn chế xem trước, để xem đầy đủ mời bạn chọn Tải xuống

Thông tin tài liệu

(NB) Giáo trình Lập trình ứng dụng: Phần 2 thông tin đến các bạn về hàm và con trỏ hàm, xây dựng giao diện ứng dụng bằng visual C sharp. Mời các bạn cùng tham khảo để nắm chi tiết nội dung của giáo trình.

CHƯƠNG HÀM VÀ CON TRỎ HÀM 5.1 HÀM Hàm nhận (hoặc không) đối số trả lại (hoặc khơng) giá trị cho chương trình gọi Trong trường hợp không trả lại giá trị, hàm hoạt động thủ tục ngơn ngữ lập trình khác Một chương trình tập hàm, có hàm với tên gọi main(), chạy chương trình, hàm main() chạy gọi đến hàm khác Kết thúc hàm main() kết thúc chương trình Hàm giúp cho việc phân đoạn chương trình thành mơđun riêng rẽ, hoạt động độc lập với ngữ nghĩa chương trình lớn, có nghĩa hàm sử dụng chương trình mà sử dụng chương trình khác, dễ cho việc kiểm tra bảo trì chương trình Hàm có số đặc trưng: - Nằm ngồi văn có chương trình gọi đến hàm Trong văn chứa nhiều hàm; - Được gọi từ chương trình (main()), từ hàm khác từ (đệ quy); - Khơng lồng nhau; - Có cách truyền giá trị: Truyền theo tham trị, tham biến tham trỏ 5.1.1 Khai báo định nghĩa hàm Khai báo Một hàm thường làm chức năng: tính tốn tham đối cho lại giá trị kết quả, đơn thực chức đó, khơng trả lại kết tính tốn Thơng thường kiểu giá trị trả lại gọi kiểu hàm Các hàm thường khai báo đầu chương trình Các hàm viết sẵn khai báo file nguyên mẫu *.h Do đó, để sử dụng hàm này, cần có thị #include đầu chương trình, *.h tên file cụ thể có chứa khai báo hàm sử dụng (ví dụ để sử dụng hàm toán học ta cần khai báo file nguyên mẫu math.h) Đối với hàm người lập trình tự viết, cần phải khai báo Khai báo hàm sau: (d/s kiểu đối) ; đó, kiểu giá trị trả lại gọi kiểu hàm nhận kiểu chuẩn C++ kiểu NSD tự tạo Đặc biệt hàm khơng trả lại giá trị kiểu giá trị trả lại khai báo void Nếu kiểu giá trị trả lại bỏ qua chương trình ngầm định hàm có kiểu int (phân biệt với void!) Ví dụ sau vài khai báo hàm: int bp(int); // Khai báo hàm bp, có đối kiểu int kiểu hàm int int rand100(); // Không đối, kiểu hàm (giá trị trả lại) int void alltrim(char[ ]); // đối xâu kí tự, hàm khơng trả lại giá trị (không kiểu) cong(int, int); // Hai đối kiểu int, kiểu hàm int (ngầm định) Thông thường để chương trình rõ ràng nên tránh lạm dụng ngầm định Ví 93 dụ khai báo cong(int, int); nên khai báo rõ kiểu hàm (trong trường hợp kiểu hàm ngầm định int) sau : int cong(int, int); Định nghĩa hàm Cấu trúc hàm bố trí giống hàm main() phần trước Hàm có trả giá trị Cú pháp: (danh sách tham đối hình thức) { khai báo cục hàm ; // dùng riêng cho hàm dãy lệnh hàm ; return (biểu thức trả về); // nằm dãy lệnh } Trong đó: - Danh sách tham đối hình thức gọi ngắn gọn danh sách đối gồm dãy đối cách dấu phẩy, đối biến thường, biến tham chiếu biến trỏ, hai loại biến sau ta trình bày phần tới Mỗi đối khai báo giống khai báo biến, tức cặp gồm - Với hàm có trả lại giá trị cần có câu lệnh return kèm theo sau biểu thức Kiểu giá trị biểu thức kiểu hàm khai báo phần tên hàm Câu lệnh return nằm vị trí phần câu lệnh, tuỳ thuộc mục đích hàm Khi gặp câu lệnh return chương trình tức khắc thoát khỏi hàm trả lại giá trị biểu thức sau return giá trị hàm Ví dụ 5.1: Viết hàm tính luỹ thừa n (với n nguyên) số thực double luythua(float x, int n) { int i ; // biến số double kq = ; // để lưu kết for (i=1; i b) ? a: b ; } double dmax(double a, double b) { return (a > b) ? a: b ; } Tóm lại ta có hàm: max(), cmax(), fmax(), lmax(), dmax(), việc sử dụng tên gây bất lợi cần gọi hàm C++ cho phép ta khai báo định nghĩa hàm với tên gọi, ví dụ max Khi ta có hàm: 1: int max(int a, int b) { return (a > b) ? a: b ; } 2: float max(float a, float b) { return (a > b) ? a: b ; } 3: char max(char a, char b) { return (a > b) ? a: b ; } 98 4: long max(long a, long b) { return (a > b) ? a: b ; } 5: double max(double a, double b) { return (a > b) ? a: b ; } Và lời gọi hàm dạng max(3,5), max(3.0,5), max('O', 'K') đáp ứng Chúng ta đặt vấn đề: với hàm tên vậy, chương trình gọi đến hàm Vấn đề giải dễ dàng chương trình dựa vào kiểu đối gọi để định chạy hàm Ví dụ lời gọi max(3,5) có đối kiểu nguyên nên chương trình gọi hàm 1, lời gọi max(3.0,5) hướng đến hàm số tương tự chương trình chạy hàm số gặp lời gọi max('O','K') Như đặc điểm hàm trùng tên danh sách đối chúng phải có cặp đối khác kiểu Một đặc trưng khác để phân biệt thông qua đối số lượng đối hàm phải khác (nếu kiểu chúng giống nhau) Ví dụ việc vẽ hình: thẳng, tam giác, vng, chữ nhật hình giống nhau, chúng phụ thuộc vào số lượng điểm nối toạ độ chúng Do ta khai báo định nghĩa hàm vẽ nói với chung tên gọi Chẳng hạn: // vẽ đường thẳng AB void ve(Diem A, Diem B) ; // vẽ tam giác ABC void ve(Diem A, Diem B, Diem C) ; void ve(Diem A, Diem B, Diem C, Diem D) ; // vẽ tứ giác ABCD Trong ví dụ ta giả thiết Diem kiểu liệu lưu toạ độ điểm hình Hàm ve(Diem A, Diem B, Diem C, Diem D) vẽ hình vng, chữ nhật, thoi, bình hành hay hình thang phụ thuộc vào toạ độ điểm ABCD, nói chung sử dụng để vẽ tứ giác Tóm lại nhiều hàm định nghĩa chồng (với tên gọi giống nhau) chúng thoả điều kiện sau: - Số lượng tham đối hàm khác nhau, - Kiểu tham đối hàm khác 5.1.5 Biến, đối tham chiếu Một biến gán cho bí danh mới, chỗ xuất biến tương đương dùng bí danh ngược lại, bí danh gọi biến tham chiếu Ý nghĩa thực tế cho phép “tham chiếu” tới biến khác kiểu nó, tức sử dụng biến khác tên biến tham chiếu Giống khai báo biến bình thường, nhiên trước tên biến ta thêm dấu (&) Có thể tạm phân biến thành loại: biến thường với tên thường, biến trỏ với dấu * trước tên biến tham chiếu với dấu & & = ; Cú pháp khai báo cho phép ta tạo biến tham chiếu cho tham chiếu đến biến tham chiếu (cùng kiểu phải khai báo từ trước) Khi biến tham chiếu cịn gọi bí danh biến tham chiếu Chú ý khơng có cú pháp khai báo tên biến tham chiếu mà khơng kèm theo khởi tạo Ví dụ: int hung, dung ; int &ti = hung; // khai báo biến nguyên hung, dung // khai báo biến tham chiếu ti, teo tham chieu đến 99 int &teo = dung; // dung ti, teo bí danh hung, dung Từ vị trí trở việc sử dụng tên hung, ti dung, teo Ví dụ: = ; // tương đương ++; ti ++; printf("%d, %d",hung, ti); // 3 teo = ti + ; // tương đương dung = + // tương đương teo ++ dung ++ ; printf("%d, %d",dung,teo); // 7 Vậy sử dụng thêm biến tham chiếu để làm gì? Cách tổ chức bên biến tham chiếu khác với biến thường chỗ nội dung địa biến mà đại diện (giống biến trỏ), ví dụ câu lệnh: printf("%d", teo) ; // in giá trị thực chất nội dung biến teo, nội dung teo địa dung, cần in teo, chương trình tham chiếu đến dung in nội dung dung (7) Các hoạt động khác teo (ví dụ teo++), thực chất tăng đơn vị nội dung dung (chứ teo) Từ cách tổ chức biến tham chiếu ta thấy chúng giống trỏ thuận lợi chỗ truy cập đên giá trị biến tham chiếu (dung) ta cần ghi tên biến tham chiếu (teo) khơng cần thêm tốn tử (*) trước trường hợp dùng trỏ Điểm khác biệt có ích sử dụng để truyền đối cho hàm với mục đích làm thay đổi nội dung biến Chú ý: - Biến tham chiếu phải khởi tạo khai báo - Tuy giống trỏ khơng dùng phép tốn trỏ cho biến tham chiếu Nói chung nên dùng truyền đối cho hàm 5.1.6 Cách truyền tham số Có cách truyền tham đối thực cho tham đối hình thức lời gọi hàm Trong cách ta dùng thời điểm gọi truyền theo tham trị, tức đối hình thức nhận giá trị cụ thể từ lời gọi hàm tiến hành tính tốn trả lại giá trị Để dễ hiểu cách truyền đối xem qua cách thức chương trình thực với đối thực hàm 5.1.6.1 Truyền theo tham trị Ta xét lại ví dụ hàm luythua(float x, int n) tính xn Giả sử chương trình ta có biến a, b, f chứa giá trị a = 2, b = 3, f chưa có giá trị Để tính ab gán giá trị tính cho f, ta gọi f = luythua(a,b) Khi gặp lời gọi này, chương trình tổ chức sau: - Tạo biến (tức nhớ nhớ) có tên x n Gán nội dung ô nhớ giá trị lời gọi, tức gán (a) cho x (b) cho n; - Tới phần khai báo (của hàm), chương trình tạo thêm nhớ mang tên kq i; 100 - Tiến hành tính tốn (gán lại kết cho kq); - Cuối lấy kết kq gán cho ô nhớ f (là nhớ có sẵn khai báo trước, nằm bên hàm); - Kết thúc hàm quay chương trình gọi Do hàm luythua() hồn thành xong việc tính tốn nên nhớ tạo thực hàm để lưu trữ x, n, kq, i xoá khỏi nhớ Kết tính tốn lưu giữ nhớ f (khơng bị xố khơng liên quan đến hàm) Trên truyền đối theo cách thông thường Vấn đề đặt giả sử ngồi việc tính f, ta muốn thay đối giá trị nhớ a, b (khi truyền cho hàm) thực khơng? Để giải toán ta cần theo kỹ thuật khác, nhờ vào vai trò biến trỏ tham chiếu 5.1.6.2 Truyền trỏ Xét ví dụ tráo đổi giá trị biến Đây yêu cầu nhỏ gặp nhiều lần chương trình, ví dụ để xếp danh sách Do cần viết hàm để thực yêu cầu Hàm không trả kết Do biến cần trao đổi chưa biết trước thời điểm viết hàm, nên ta phải đưa chúng vào hàm tham đối, tức hàm có hai tham đối x, y đại diện cho biến thay đổi giá trị sau Từ vài nhận xét trên, theo thông thường hàm tráo đổi viết sau: void doi_cho(int x, int y) { int t ; t=x; x=y; y=t; } Giả sử chương trình ta có biến x, y chứa giá trị 2, Ta cần đổi nội dung biến cho x = y = cách gọi đến hàm doi_cho(x, y) int main() { int x = 2; int y = 5; doi_cho(x, y) ; printf("%d, %d",x, y); // getch(); return 0; } 101 2, (x, y không đổi) Thực sau chạy xong chương trình ta thấy giá trị x y khơng thay đổi !? Như giải thích mục (gọi hàm luythua()), việc chương trình thực hàm tạo biến (các ô nhớ mới, độc lập với ô nhớ x, y có sẵn) tương ứng với tham đối, trường hợp có tên x, y gán nội dung x, y (ngoài hàm) cho x, y (mới) Và việc cuối chương trình sau thực xong hàm xoá biến Do nội dung biến thực có thay đổi, khơng ảnh hưởng đến biến x, y cũ Hình vẽ minh hoạ cách làm việc hàm doi_cho(), trước, sau gọi hàm Hình 3.3 Sự thay đổi giá trị tham số thực Như hàm doi_cho() cần viết lại cho việc thay đối giá trị không thực biến tạm mà phải thực thực biến ngồi Muốn thay truyền giá trị biến cho đối, ta truyền địa cho đối, thay đổi phải thực nội dung địa Đó lý ta phải sử dụng trỏ để làm tham đối thay cho biến thường Cụ thể hàm swap viết lại sau: void doi_cho(int *p, int *q) { int t; t = *p ; *p = *q ; *q = t ; // khai báo biến tạm t // đặt giá trị t nội dung nơi p trỏ tới // thay nội dung nơi p trỏ nội dung nơi q trỏ // thay nội dung nơi q trỏ tới nội dung t } Với cách tổ chức hàm rõ ràng ta cho p trỏ tới biến x q trỏ tới biến y hàm doi_cho() thực làm thay đổi nội dung x, y p, q Từ lời gọi hàm doi_cho(&x, &y) (tức truyền địa x cho p, p trỏ tới x tương tự q trỏ tới y) Như tóm tắt đặc trưng để viết hàm làm thay đổi giá trị biến sau: - Đối hàm phải trỏ (ví dụ int *p); - Các thao tác liên quan đến đối (trong thân hàm) phải thực nơi trỏ đến (ví dụ *p = …); 102 Hình 6.15 Kết thực thi ứng dụng 6.4 ĐIỀU KHIỂN LED VỚI ARDUINO VÀ C# 6.4.1 Phần cứng: Phần cứng tương tự dự án bật tắt led bình thường     Arduino UNO 1x led 1x điện trở 1k Phần mềm Microsoft Visual C# 6.4.2 Sơ đồ nối dây: Hình 6.16 Sơ đồ nối dây 150 6.4.3 Phần mềm: Code arduino: int val; int led = 13; void setup() { pinMode(led, OUTPUT); Serial.begin(9600); } void loop() { while (Serial.available()) { val = Serial.read(); 10 Serial.println(val); 11 delay(200); 12 } 13 if (val == '1') { 14 digitalWrite(led, LOW); 15 } else if (val == '2') { 16 digitalWrite(led, HIGH); 17 } 18 } Thiết kế giao diện điều khiển: Trên hình Microsoft Visual C# nhấp chọn ToolBox kéo thả đối tượng: Button, serialPort, Label, ComboBox, Timer,….như giao diện Sau nhấp đúp chuột vào đối tượng để viết code cho đối tượng 151 Hình 6.17 Giao diện điều khiển // Code điều khiển using System; using System.Collections.Generic; using System.ComponentModel; using System.Data; using System.Drawing; using System.Linq; using System.Text; using System.Windows.Forms; 10 // Phần phần khởi tạo mặc định bạn không cần quan tâm 11 using System.IO.Ports; // Thêm dòng Code để dùng lệnh với Serial.Port 12 13 namespace Dieukhien 14 { 15 public partial class Form1 : Form 16 { 152 17 public Form1() 18 { 19 InitializeComponent(); 20 } 21 22 private void Form1_Load(object sender, EventArgs e) // Khi phần mềm mở 23 { 24 comboBox1.DataSource = SerialPort.GetPortNames();//Quét cổng Serial hoạt động lên ComboBox1 25 26 } 27 28 private void button1_Click(object sender, EventArgs e)// 29 { 30 if (!serialPort1.IsOpen) // Nếu đối tượng serialPort1 chưa mở , sau nhấn button thỳ… 31 { 32 33 serialPort1.PortName = comboBox1.Text;//cổng serialPort1 = ComboBox mà bạn chọn 34 serialPort1.Open();// Mở cổng serialPort1 35 36 37 } 38 private void button4_Click(object sender, EventArgs e)// 39 { 40 41 serialPort1.Close();//Đóng cổng Serial sau button nhấn 42 } 43 44 } 45 46 private void button2_Click(object sender, EventArgs e) 153 47 { 48 serialPort1.Write("2");//Nếu button2 nhấn,gửi byte “1” đến cổng serialPort1 49 } 50 51 private void button3_Click(object sender, EventArgs e) 52 { 53 serialPort1.Write("1");//gửi byte “0” đến cổng serialPort1 54 } 55 56 private void tácGiảToolStripMenuItem1_Click(object sender, EventArgs e) 57 { 58 MessageBox.Show("Phần mềm viết Ðỗ Hữu Toàn (Bạn Ðinh Hồng Thái)", "Tác giả");// Nếu MenuTrip tác giả nhấn thỳ lên hộp thoại 59 } 60 61 private void thoátToolStripMenuItem_Click(object sender, EventArgs e) 62 { 63 Application.Exit(); // Nếu ấn thốt…Thốt chương trình 64 } 65 66 private void timer1_Tick(object sender, EventArgs e) 67 { 68 if (!serialPort1.IsOpen) { 69 button1.Text = ("Kết nối"); 70 label3.Text = ("Chưa kết nối"); 71 label3.ForeColor = Color.Red; 72 //Nếu Timer làm mới, Cổng serialPort1 chưa mở thay đổi Text button1, label3…đổi màu text label3 thành màu đỏ 73 } 74 else if (serialPort1.IsOpen) { 75 button1.Text = ("Ngắt kết nối"); 76 label3.Text = ("Ðã kết nối"); 77 label3.ForeColor = Color.Green; 154 78 //Nếu Timer làm mới, Cổng serialPort1 mở thay đổi Text button1, label3…đổi màu text label3 thành màu xanh 79 80 } 81 } 82 83 } 84 } 6.5 BÀI TẬP Thêm vào Project 6.3.4 Form frmUocboi, thực tìm “Ước số chung lớn ” “Bội số chung nhỏ nhất” số nguyên A B: Yêu cầu: - Viết hàm tìm USCLN BSCNN số a b Nếu ta chọn Option USCLN xuất kết ước số chung lớn hay ngược lại bội số chung nhỏ - Nút bỏ qua dùng để xóa rỗng Textbox - Nút Thốt có xuất thơng báo Viết chương trình nhập vào số a, b c cho biết số lớn nhỏ số a, b c với giao diện sau 155 Hướng dẫn gợi ý: sử dụng cấu trúc If …Else Viết chương trình nhập vào giá trị ngun dương N, tính tổng S = + + +…+ N với giao diện sau 156 TÀI LIỆU THAM KHẢO [1] D.E Knuth, The Art of Computer Programming, Volume 1, Fundamental Algorithms, Addison-Wesley, Reading, MA,1973 [2] D.E Knuth, The Art of Computer Programming, Volume 2, Searching and Sorting, AddisonWesley, Reading, MA,1973 [3] Francis Scheid, Singapore,1983 Computers and Programming, McGraw-Hill Book Company, [4] Ian Parberry, Algorithm Analysis and Complexity, Depart of Computer Sciences, University of North Texas, 2001 [5] Ian Parberry, William Gasarch, Problems on Algorithms, Prentice-Hall, 2002 [6] Jon Bentley, Programming Pearls, 2nd Edition, Addison-Wesley, Inc., 2000 [7] N Wirth, Data Structure + Algorithm = Programs, Pretice-Hall Inc 1976 [8] Peter Juliff, Program Design, 2nd Edition, Prentice-Hall, 1986 [9] William B Jones, Programming Concepts, Prentice-Hall, Inc., 1982 157 PHỤ LỤC Source Code: 2.5.1 – Bài /* Vi du - Tinh dien tich tam giac biet chieu cao va canh day */ #include #include #include // Chuong trinh chinh int main() { int a,h; // a - chieu dai day, h - chieu cao float s; // Dien tich tam gia system("cls"); // Xoa man hinh printf("Nhap vao a va h:"); scanf("%d %d",&a,&h); s=a*h; printf("Dien tich bang ", s); printf("Nhan phim bat ky de ket thuc!"); getch(); // Dung doi nhan phim bat ky return 0; } 2.5.1 – Bài /* Chuong trinh tinh TONG, HIEU, TICH, THUONG so*/ #include #include #include /* Chuong trinh chinh */ int main() { /* Khai bao bien va chuan bi*/ int a,b; float tong, hieu,tich, thuong; 158 system("cls"); /* Huong dan nhap va Nhap du lieu vao*/ printf("Nhap vao A va B:"); scanf("%d %d",&a,&b); /* Tinh toan TONG, HIEU, TICH, THUONG*/ tong=a+b; hieu=a-b; tich=a*b; thuong=a/b; /* Trinh bay ket qua r*/ printf("Tong %d + %d = %10.2f\n", a,b,tong); printf("Hieu %d - %d = %10.2f\n", a,b,hieu); printf("Tich %d * %d = %10.2f\n", a,b,tich); printf("Thuong %d / %d = %10.2f\n", a,b,thuong); printf("Nhan phim bat ky de ket thuc!"); /* Doi nhan phim bat ky de ket thuc*/ getch(); return 0; } 4.4.1 #include #include int main() { int b[20], N; int i, ln; printf("So phan tu thuc te cua mang N= "); scanf("%d",&N); for(i=0; i< N; i++) { printf("Phan tu thu %d: ",i);scanf("%d",&b[i]); } ln = b[0]; 159 for(i=1; i< N; i++) { if (b[i]>ln) { ln=b[i]; } } printf("Gia tri lon nhat la: %d", ln); getch(); return 0; } 4.4.2 #include #include #define N #define M int main() { int i, j,k; int a[N][M], b[M][N], c[N][N]; //nhap du lieu cho mang a printf("Nhap ma tran A[%d][%d]:\n",N,M); for(i=0;i

Ngày đăng: 29/10/2020, 22:45

Từ khóa liên quan

Tài liệu cùng người dùng

  • Đang cập nhật ...

Tài liệu liên quan