Bài giảng Giới thiệu lập trình - Giới thiệu - Lê Nguyên Khôi
Tóm tắt Bài giảng Giới thiệu lập trình - Giới thiệu - Lê Nguyên Khôi: ...<= 5"; Cấu Trúc Lựa Chọn if else loại bỏ trường hợp không cần thiết 20 if (!a && !b) output = false; else if (!a && b) output = true; else if (a && !b) output = true; else if (a && b) output = true; Phân tích và loại trường hợp không cần thiết if (!a && !b) output = false; else output ...p Trình // khai báo hàm trước int main() int A(); int B(); int main() { return 0; } // định nghĩa hàm sau int main() int A() { B(); } int B() { A(); } Hàm – Tính Nhân (Trả Về int) chỉ sử dụng phép cộng 16Giới Thiệu Lập Trình int multiply(int x, int y) { int ketQua = 0; for (i...húc xâu Ví dụ: Xâu "hello" lưu dưới dạng cstring Khai báo char s[10];, s lưu 9 ký tự và '\0' Lưu xâu sử dụng mảng không đầy: Khai báo một mảng “đủ lớn” để lưu xâu Ký tự null ('\0') đánh dấu kết thúc xâu Giới Thiệu Lập Trình Xâu Ký Tự cstring – Ví Dụ 3 Khai báo char s[10]; ...
outStream.open("outfile.txt"); int so1, so2, so3; inStream >> so1 >> so2 >> so3; outStream << "Tong 3 so dau la " << (so1 + so2 + so3) << endl; inStream.close(); outStream.close(); Giới Thiệu Lập Trình Ghi Dữ Liệu Vào Tệp 13 Thường một tệp được mở là một tệp rỗng Nếu tệp tồn tại, toàn bộ dữ liệu bị xóa Mở tệp để chèn vào cuối tệp (sử dụng cờ): ofstream outStream; outStream.open("outfile.txt", ios::app); Nếu tệp không tồn tại, tạo tệp mới Nếu tệp tồn tại, chèn vào cuối tệp Tham số thứ 2 là hằng trong lớp ios Trong thư viện iostream Không gian tên std Giới Thiệu Lập Trình Kiểm Tra Mở Tệp Thành Công 14 Có thể gặp lỗi khi mở tệp Khi tệp không tồn tại (để đọc dữ liệu) Không có quyền ghi vào tệp Sử dụng hàm thành viên fail() Gọi hàm thành viên fail() để kiểm tra mở luồng thành công không inStream.open("infile.txt"); if (inStream.fail()) { cout << "Loi mo file.\n"; exit(1); } Giới Thiệu Lập Trình Kiểm Tra Kết Thúc Tệp 15 Dùng vòng lặp để xử lý với tệp đến khi hết tệp Sử dụng hàm thành viên eof() inStream.get(next); while (!inStream.eof()) { cout << next; inStream.get(next); } Đọc từng ký tự cho đến khi hết dữ liệu trong tệp Hàm thành viên eof() trả về kiểu bool Giới Thiệu Lập Trình Nhập Tên Tệp Khi Chạy Chương Trình 16 Tham số cho open() là kiểu xâu ký tự Tên cụ thể hoặc biến char tenTep[16]; cout << "Nhap ten tep: "; cin >> tenTep; ifstream inStream; inStream.open(tenTep); Linh hoạt hơn đối với tên tệp là biến được nhập từ bàn phím khi chạy chương trình Giới Thiệu Lập Trình Định Dạng Dữ Liệu Xuất 17 Xuất dữ liệu dưới dạng 2 số thập phân: cout.setf(ios::fixed); cout.setf(ios::showpoint); cout.precision(2); In ra màn hình (12.50) Hàm thành viên precision(x) Phần thập phân dưới dạng "x" số sau dấu “.” Hàm thành viên setf() Cho cài đặt nhiều định dạng Có thể sử dụng cho bất cứ luồng xuất nào Đối với luồng cho tệp, hàm thành viên giống đối tượng cout Giới Thiệu Lập Trình 4Tham Khảo 18 Đọc sách: Chương 8, Lập Trình Cơ Bản C++ Tìm hiểu thư viện iomanip Các định dạng xuất dữ liệu Tìm hiểu thao tác với tệp truy cập ngẫu nhiên Hiểu quả cho cơ sở dữ liệu lớn Giới Thiệu Lập Trình 1Giới Thiệu Lập Trình Con Trỏ TS. Lê Nguyên Khôi Trường Đại học Công nghệ, ĐHQGHN Nội Dung 1 Con trỏ Biến kiểu con trỏ Quản lý vùng nhớ Toán tử con trỏ Mảng động Khai báo & sử dụng Các phép toán với con trỏ Giới Thiệu Lập Trình Giới Thiệu 2 Định nghĩa: Địa chỉ vùng nhớ máy tính của một biến Vùng nhớ máy tính Chia nhỏ thành các byte Đánh số thứ tự lần lượt (hệ 16) Địa chỉ được sử dụng làm tên cho biến Con trỏ đã sử dụng Truyền tham số theo kiểu tham chiếu Địa chỉ của tham số được truyền Giới Thiệu Lập Trình Biến Con Trỏ 3 Con trỏ là “kiểu dữ liệu” Kiểu địa chỉ vùng nhớ Có thể dùng biến để lưu giá trị kiểu con trỏ Không phải kiểu int, double Địa chỉ của vùng nhớ dùng lưu dữ liệu kiểu int, double Ví dụ: double * p; Khai báo p là biến kiểu con trỏ double Lưu địa chỉ vùng nhớ kiểu double Giới Thiệu Lập Trình Biến Con Trỏ – Khai Báo 4 Khai báo con trỏ giống biến kiểu dữ liệu khác Thêm * vào trước tên biến Ký hiệu * phải đặt trước mỗi biến con trỏ Ví dụ: int *p1, *p2, v1, v2; p1, p2 biến kiểu con trỏ int v1, v2 biến kiểu int Sử dụng p1, p2 lưu địa chỉ các biến kiểu int Sử dụng p1, p2 lưu địa chỉ của v1, v2 Giới Thiệu Lập Trình Địa Chỉ & Số Nguyên 5 Con trỏ là địa chỉ Địa chỉ là số nguyên Con trỏ KHÔNG là số nguyên C++ ép con trỏ phải được sử dụng như địa chỉ Không thể được sử dụng như số nguyên Mặc dù đó là số nguyên!!! Giới Thiệu Lập Trình 2Toán Tử & 6 Toán tử & trả về địa chỉ của biến Dòng 4: đặt biến con trỏ p chỉ tới biến v1 p bằng địa chỉ của v1 Dòng 5: đặt biến con trỏ p chỉ tới biến v2 p chỉ tới v1 Giới Thiệu Lập Trình 1 { 2 int *p, v1, v2; 3 v1 = 10; v2 = 20; 4 p = &v1; 5 p = &v2; 6 } 0x22ff32 p 20 v2 0x22ff32 0x44ab12 p 10 v1 0x44ab12 Toán Tử * 7 Toán tử * truy xuất giá trị của vùng nhớ được quản lý (lưu) bởi con trỏ Dòng 4: in ra 10 (giá trị biến v1, mà p chỉ tới) Dòng 6: in ra 20 (giá trị biến v2, mà p chỉ tới) Giới Thiệu Lập Trình 1 { 2 int *p, v1, v2; 3 v1 = 10; p = &v1; 4 cout << *p; 5 v2 = 20; p = &v2; 6 cout << *p; 7 } 0x22ff32 p 20 v2 0x22ff32 0x44ab12 p 10 v1 0x44ab12 Toán Tử = 8 Gán giá trị Dòng 3, 4: p chỉ tới v1, q chỉ tới v2 Dòng 5: sử dụng toán tử * truy cập vùng tới nhớ con trỏ quản lý *p là v1, *q là v2, dòng 5 tương đương v1 = v2; Giới Thiệu Lập Trình 1 { 2 int v1 = 10, v2 = 20; 3 int *p = &v1; 4 int *p = &v2; 5 *p = *q; 6 } 0x22ff32 q 20 v2 0x22ff32 0x44ab12 p 10 20 v1 0x44ab12 Toán Tử = 9 Gán con trỏ Dòng 3, 4: p chỉ tới v1, q chỉ tới v2 Dòng 5: gán p bằng q p không quản lý v1 p và q cùng quản lý v2 Giới Thiệu Lập Trình 1 { 2 int v1 = 10, v2 = 20; 3 int *p = &v1; 4 int *p = &v2; 5 p = q; 6 } 0x22ff32 q 20 v2 0x22ff32 0x44ab12 p 10 v1 0x44ab12 0x22ff32 Bài Tập 10Giới Thiệu Lập Trình 1 { 2 int i = 10, j = 20, k; 3 int *p = &i; 4 int *q = &j; 5 *p += 1; 6 p = &k; 7 *p = *q; 8 p = q; 9 *p = i; 0 } j 0x7756 p 0x64cc p 0x16aa k 0x9948 i 0x2232 Toán Tử new 11 Sử dụng toán tử new để tạo một vùng nhớ mới cho con trỏ, vùng nhớ này không có tên int * p = new int; Khởi tạo một vùng nhớ mới cho con trỏ p, giá trị tại vùng nhớ này không biết int * p = new int(10); Khởi tạo một vùng nhớ mới cho con trỏ p, giá trị tại vùng nhớ này được khởi tạo là 10 Giới Thiệu Lập Trình 3Bài Tập 12Giới Thiệu Lập Trình 1 { 2 int *p1, *p2; 3 p1 = new int; 4 *p1 = 10; 5 p2 = p1; 6 *p2 = 20; 7 p1 = new int; 8 *p1 = 30; 9 } ?p1 ?p2 p1 ?p2 ? p1 ?p2 10 p1 p2 10 p1 p2 20 p1 p2 20 ? p1 p2 20 30 Toán Tử delete 13 Sử dụng toán tử delete để giải phóng vùng nhớ động được tạo ra bởi toán tử new Lưu ý: chỉ giải phóng vùng nhớ được tạo ra bởi new, không phải xóa biến con trỏ p Giới Thiệu Lập Trình { int * p = new int; delete p; } Toán Tử delete 14 Vùng nhớ động có thể được trả về bởi hàm Vùng nhớ động chỉ được giải phóng khi sử dụng delete, do đó vùng nhớ động tạo ra trong hàm không bị xóa sau khi kết thúc hàm Chỉ các biến khai báo trong hàm bị xóa, trong đó có biến con trỏ p Giới Thiệu Lập Trình int * f(int * q) { int * p = new int; return p; } Mảng Động 15 Biến mảng thực chất là biến con trỏ Mảng thông thường (int a[10]) Độ dài mảng cố định Không thể thay đổi độ dài sau khi khai báo Có thể coi là con trỏ hằng (con trỏ tĩnh) Mảng động (int * a = new int[10]) Độ dài mảng có thể thay đổi sau khi khai báo Sử dụng lại toán tử new int * a = new int[10]; a = new int[50]; Giới Thiệu Lập Trình Mảng Động – Mảng Tĩnh 16 int * a = new int[10]; int * p; a và p đều là biến con trỏ, nhưng a là hằng Có thể gán (được phép) p = a; p chỉ tới địa chỉ mà a đang chỉ tới Nhưng không được phép (lỗi dịch) a = p; a là hằng, không thay đổi giá trị của a Giới Thiệu Lập Trình Nhắc Lại: cstring & Lớp string 17 char aCString[]; string stringVar; Chuyển cstring sang string (hợp lệ) stringVar = aCString; Chuyển string sang cstring (không hợp lệ) aCString = stringVar; Giới Thiệu Lập Trình 4Mảng Động 18 Hạn chế của mảng thông thường: Phải khai báo độ dài trước Độ dài mảng có thể không biết tới khi chạy chương trình Phải ước lượng độ dài lớn nhất Lãng phí bộ nhớ Mảng động Có thể tăng và giảm khi cần thiết Giới Thiệu Lập Trình Giải Phóng Mảng Động 19 Cũng được thực hiện khi chạy d = new double[10]; // thao tác với d delete [] d; Giải phóng tất cả bộ nhớ cho mảng động [] thông báo giải phóng bộ nhớ cho mảng Vẫn chỉ tới vùng nhớ đó Nên gán d = NULL; Giới Thiệu Lập Trình Bài Tập 20Giới Thiệu Lập Trình int a[10] = {2,3,5,1,4,7,0}; int *p = a; cout << a[0] << *p << "\n"; p++; cout << *p << p[2] << "\n"; p++; a[2] = 0; cout << p[1] << *p << "\n"; p -= 2; cout << p[3] << p[1] << "\n"; 2 2 3 1 1 9 1 3 Hàm Trả Về Mảng 21 Kiểu mảng không được phép là kiểu trả về Không hợp lệ int[] someFunction(); Phải trả về kiểu con trỏ int * someFunction(); Giới Thiệu Lập Trình Con Trỏ Trong C++ 22 Con trỏ là khối kiến thức đặc biệt quan trọng trong C++ Phải nắm vững khái niệm con trỏ cũng như thao tác với con trỏ Con trỏ sẽ được sử dụng trong các kiểu dữ liệu phức tạp INT 2203 Cấu trúc Dữ liệu & Giải thuật Giới Thiệu Lập Trình 1Giới Thiệu Lập Trình Cấu Trúc struct TS. Lê Nguyên Khôi Trường Đại học Công nghệ, ĐHQGHN Nội Dung 1 Cấu trúc struct Kiểu dữ liệu nhóm Định nghĩa Khai báo / Khởi tạo Sử dụng Truyền biến cho hàm Giới Thiệu Lập Trình Kiểu Dữ Liệu Nhóm 2 Kiểu Mảng: Tập hợp dữ liệu cùng kiểu Khai báo sau đó sử dụng như biến đơn lẻ Truyền cho hàm: truyền địa chỉ Kiểu cấu trúc struct: Tập hợp dữ liệu có thể khác kiểu Phải định nghĩa trước khi sử dụng Khai báo sau đó sử dụng như biến đơn lẻ Truyền cho hàm: giống biến đơn lẻ Giới Thiệu Lập Trình Kiểu DL Cấu Trúc struct 3 Tập hợp dữ liệu, có thể khác kiểu, được nhóm Mỗi dữ liệu được lưu trong một biến (trường) Mỗi dữ liệu có kiểu dữ liệu cụ thể Hỗ trợ tổ chức dữ liệu phức tạp vào cùng một đối tượng Hỗ trợ làm việc giữa các dữ liệu trên đối tượng Giới Thiệu Lập Trình Kiểu DL Cấu Trúc struct – Ví Dụ 4 Tên Trường Kiểu Dữ Liệu Dữ Liệu MSSV string 12345678 HoTen string Trach Van Doanh NgaySinh string 01/01/1999 GioiTinh bool true Giới Thiệu Lập Trình Kiểu DL Cấu Trúc struct – Định Nghĩa 5 Định nghĩa bởi từ khóa struct Định nghĩa toàn cục Ngoài và trước int main() Tất cả các hàm đều hiểu Không được cấp phát bộ nhớ Chỉ có mục đích miêu tả cấu trúc Chỉ cấp phát bộ nhớ Khi khai báo biến kiểu cấu trúc Miêu tả: Các thành phần (trường) và kiểu của chúng Giới Thiệu Lập Trình 2struct sinhvien – Định Nghĩa 6 struct sinhvien { string MSSV; string HoTen; string NgaySinh; bool GioiTinh; } ; Giới Thiệu Lập Trình Tên Trường Kiểu Dữ Liệu Dữ Liệu MSSV string 12345678 HoTen string Trach Van Doanh NgaySinh string 01/01/1999 GioiTinh bool true struct sinhvien – Khai Báo/Khởi Tạo 7 struct sinhvien { string MSSV; string HoTen; string NgaySinh; bool GioiTinh; } ; int main() { struct sinhvien sv1; struct sinhvien sv2 = { "12345678" , "Trach Van Doanh" , "01/01/1999" , true } ; } Giới Thiệu Lập Trình Truy Cập Thành Phần struct 8 Sử dụng toán tử chấm (.) sv1 . MSSV sv1 . HoTen sv1 . NgaySinh sv1 . GioiTinh Gọi tên là “biến thành phần” Các thành phần của biến kiểu cấu trúc Kiểu cấu trúc struct khác nhau có thể có cùng tên biến thành phần Biến thành phần là biến cục bộ Giới Thiệu Lập Trình Truy Cập Thành Phần struct – Ví Dụ 9 struct sinhvien { string MSSV; string HoTen; string NgaySinh; bool GioiTinh; } ; int main() { struct sinhvien sv1; sv1.MSSV = "12345678"; sv1.HoTen = "Trach Van Doanh"; sv1.NgaySinh = "01/01/1999"; sv1.GioiTinh = true; } Giới Thiệu Lập Trình struct ngaythangnam 10 struct ngaythangnam { int ngay; int thang; int nam; } ; int main() { struct ngaythangnam homNay = {1, 4, 2000}; struct ngaythangnam ngayMai; ngayMai.ngay = homNay.ngay + 1; ngayMai.thang = homNay.thang; ngayMai.nam = homNay.nam; } Giới Thiệu Lập Trình Cấu Trúc struct – Phép Gán 11 Với cấu trúc struct ngaythangnam Khai báo 2 biến cấu trúc struct ngaythangnam homQua, homNay; Cả 2 biến đều kiểu struct ngaythangnam Thực hiện phép gán đơn giản hợp lệ homQua = homNay; Sao chép giá trị biến thành phần homNay của cho các biến thành phần của homQua, tương đương homQua.ngay = homNay.ngay; homQua.thang = homNay.thang; homQua.nam = homNay.nam; Giới Thiệu Lập Trình 3Cấu Trúc struct – Phép Toán Khác 12 Các phép toán khác không được định nghĩa cho kiểu cấu trúc struct So sánh bằng/khác (==, !=) (homQua == homNay biểu thức không hợp lệ) So sánh thứ tự (, ...) (homQua < homNay biểu thức không hợp lệ) Các phép toán (homQua + homNay biểu thức không hợp lệ) Nhập & in (cin & cout không hợp lệ) Giới Thiệu Lập Trình Truyền Biến Cấu Trúc struct Cho Hàm 13 struct toado { int x, y; } ; typedef struct toado ToaDo; void _nhapToaDo(ToaDo & td) { cin >> td.x >> td.y; } void _inToaDo(const ToaDo & td) { cout << "(" << td.x << "," << td.y << ")"; } Giới Thiệu Lập Trình Truyền Biến Cấu Trúc struct Cho Hàm 14 struct toado { int x , y ; } ; typedef struct toado ToaDo; void _nhapToaDo ( ToaDo & td ) ; void _inToaDo ( const ToaDo & td ) ; int main ( ) { ToaDo td1; _nhapToaDo ( td1 ) ; _inToaDo ( td1 ) ; ToaDo td2; _nhapToaDo ( td2 ) ; _inToaDo ( td2 ) ; } Giới Thiệu Lập Trình Truyền Biến Cấu Trúc struct Cho Hàm 15 void _trungDiem ( const ToaDo & td1 , const ToaDo & td2 , ToaDo & trungDiem ) { trungDiem.x = ( td1.x + td2.x ) / 2; trungDiem.y = ( td1.y + td2.y ) / 2; } ToaDo * _trungDiem ( const ToaDo & td1 , const ToaDo & td2 ) { ToaDo * trungDiem = new ToaDo; (*trungDiem).x = ( td1.x + td2.x ) / 2; (*trungDiem).y = ( td1.y + td2.y ) / 2; return trungDiem; } Giới Thiệu Lập Trình Truyền Biến Cấu Trúc struct Cho Hàm 16 int main ( ) { ToaDo td1 ; _nhapToaDo ( td1 ) ; ToaDo td2 ; _nhapToaDo ( td2 ) ; ToaDo tdTrgD1 ; _trungDiem ( td1 , td2 , tdTrgD1 ) ; ToaDo * tdTrgD2 = new ToaDo; tdTrgD2 = _trungDiem ( td1 , td2 ) ; _inToaDo ( tdTrgD1 ) ; _inToaDo ( *tdTrgD2 ) ; } Giới Thiệu Lập Trình Cấu Trúc struct & Con Trỏ 17 Giống các kiểu dữ liệu khác: struct toado * là con trỏ tới struct toado Toán tử & trả về địa chỉ của biến cấu trúc Theo thứ tự ưu tiên: “.” được ưu tiên trước “*” Nếu td là con trỏ tới cấu trúc struct toado: *p.x tương đương *(p.x) không hợp lệ Phải sử dụng (*p).x Để thuận tiện, có thể dùng toán tử ->: kết hợp con trỏ (*) với truy cập trường (.) p->a tương đương (*p).a Giới Thiệu Lập Trình 4struct thoigian 18Giới Thiệu Lập Trình struct thoigian 19Giới Thiệu Lập Trình struct sohuuti 20Giới Thiệu Lập Trình struct sohuuti 21Giới Thiệu Lập Trình struct dathuc 22Giới Thiệu Lập Trình struct dathuc 23Giới Thiệu Lập Trình 1Giới Thiệu Lập Trình Hàm – Nâng Cao TS. Lê Nguyên Khôi Trường Đại học Công nghệ, ĐHQGHN Nội Dung 1 Nhắc lại Hàm – Cơ Bản Nạp chồng hàm Nạp chồng toán tử Giới Thiệu Lập Trình Hàm – Cơ Bản 2 Khai báo hàm int bin ( int , int ) ; Định nghĩa hàm int bin ( int so1 , int so2 ) { // thân hàm miêu tả định nghĩa // không khai báo lại so1 , so2 } Chữ ký hàm int bin ( int , int ) Lời gọi hàm int a = bin ( so1 , so2 ) ; Sử dụng tên hàm, tên tham số, không có kiểu Giới Thiệu Lập Trình Hàm – Cơ Bản – Truyền Tham Số 3 Truyền giá trị int bin ( int , int ) ; Tạo và truyền một bản sao > tốn chi phí Thay đổi bản sao , bản gốc ngoài hàm không đổi Xóa bản sao khi kết thúc hàm Truyền tham chiếu int bin ( int & , int & ) ; Chính bản gốc được truyền (địa chỉ bản gốc) Thay đổi trong hàm, bản gốc thay đổi Không xóa bản gốc khi kết thúc hàm Giới Thiệu Lập Trình Hàm – Cơ Bản – Sử Dụng const 4 Truyền tham chiếu int bin ( int & , int & ) ; Thay đổi trong hàm, bản gốc thay đổi Không muốn hàm thay đổi, sử dụng từ khóa const Bảo vệ dữ liệu, không cho thay đổi, dữ liệu “chỉ-đọc” int bin ( const int & , const int & ) ; Quy ước: Luôn truyền tham chiếu Dữ liệu không thay đổi, dùng const Dữ liệu thay đổi, không dùng const Giới Thiệu Lập Trình Hàm Nạp Chồng (Function Overloading) 5 Các hàm thực hiện công việc tương tự Trùng tên, nhưng khác nhau về tham số Số lượng tham số Kiểu tham số Xác định hàm nào được gọi: Sử dụng thông tin về tham số Số lượng & kiểu tham số Kiểu của hàm Giới Thiệu Lập Trình 2Hàm Nạp Chồng – Ví Dụ 6 void _trungDiem ( const ToaDo & td1 , const ToaDo & td2 , ToaDo & trungDiem ) { trungDiem.x = ( td1.x + td2.x ) / 2; trungDiem.y = ( td1.y + td2.y ) / 2; } ToaDo * _trungDiem ( const ToaDo & td1 , const ToaDo & td2 ) { ToaDo * trungDiem = new ToaDo; (*trungDiem).x = ( td1.x + td2.x ) / 2; (*trungDiem).y = ( td1.y + td2.y ) / 2; return trungDiem; } Giới Thiệu Lập Trình Hàm Nạp Chồng 7 Khác số lượng tham số Hàm tính tổng các số truyền vào Tính tổng 3 số nguyên int _tong ( int , int , int ) ; Tính tổng 2 số nguyên int _tong ( int , int ) ; Tính tổng 1 số nguyên int _tong ( int ) ; Dựa trên số lượng tham số để gọi hàm tương ứng Giới Thiệu Lập Trình Hàm Nạp Chồng 8 Tham số mặc định int _tong(int so1, int so2 = 0, int so3 = 0) { return so1 + so2 + so3; } Có thể gọi _tong ( 1 , 2 , 3 ) _tong ( 1 , 2 ) _tong ( 1 ) Có định nghĩa hàm int _tong ( int , int ) _tong ( 1 , 2 ) gọi hàm nào Giới Thiệu Lập Trình Hàm Nạp Chồng 9 Khác kiểu tham số Hàm tính tổng 2 số truyền vào int _tong ( int , int ) ; double _tong ( double , double ) ; Dựa trên kiểu tham số để gọi hàm tương ứng Tại sao không sử dụng chuyển đổi kiểu tự động Kiểu trả về không đúng Nguy hiểm _tong(1,2) gọi int _tong(int, int); _tong(1.0,2.0) gọi double _tong(double, double); Giới Thiệu Lập Trình Hàm Nạp Chồng 10 Khác kiểu tham số Hàm tính tổng 2 số truyền vào double _tong ( int , double ) ; double _tong ( double , int ) ; Dựa trên kiểu tham số để gọi hàm tương ứng Sử dụng chuyển đổi kiểu tự động _tong ( 3 , 3 ) hoặc _tong ( 3.5 , 3.5 ) Gọi hàm nào Thêm đầy đủ int _tong ( int , int ) ; double _tong ( double , double ) ; Giới Thiệu Lập Trình Toán Tử 11 Toán tử thực chất là hàm Sử dụng toán tử giống lời gọi hàm Viết theo một cách khác Ví dụ: so sánh bằng 1 == 2 thực chất == ( 1 , 2 ) Giới Thiệu Lập Trình 3Toán Tử Nạp Chồng 12 Giống như hàm, toán tử cũng có thể nạp chồng Định nghĩa toán tử cho kiểu dữ liệu mới Nạp chồng toán tử so sánh cho kiểu cấu trúc struct PS { int ts , ms ; } ; bool operator == ( const PS & ps1 , const PS & ps2 ) { return ( ps1.ts * ps2.ms == ps2.ts * ps1.ms ) ; } bool operator != ( const PS & , const PS & ) ; Giới Thiệu Lập Trình Toán Tử Nạp Chồng 13 struct PS { int ts , ms ; } ; bool operator == ( const PS & , const PS & ) ; bool operator != ( const PS & , const PS & ) ; int main() { PS ps1 , ps2 ; // nhập dữ liệu if ( ps1 == ps2 ) if ( ps1 != ps2 ) } Giới Thiệu Lập Trình Toán Tử Nạp Chồng 14 struct PS { int ts , ms ; } ; PS operator + ( const PS & ps1 , const PS & ps2 ) { PS tongPS; // cập nhật tongPS return tongPS; } int main() { PS ps1 , ps2 , tongPS ; tongPS = ps1 + ps2 ; } Giới Thiệu Lập Trình Toán Tử Nạp Chồng 15 struct PS { int ts , ms ; } ; PS operator + ( const PS & ps , const int & i ) { PS tongPS; // cập nhật tongPS return tongPS; } int main() { PS ps , tongPS ; tongPS = ps + 1 ; } Giới Thiệu Lập Trình Toán Tử Nạp Chồng 16 ostream & operator << ( ostream & outStream , const PS & ps ) { outStream << ps.ts << "/" << ps.ms ; return outStream; } int main() { PS ps , tongPS ; tongPS = ps + 1 ; cout << tongPS; } Giới Thiệu Lập Trình Template – Giới Thiệu 17 int _getMax(int so1 , int so2) { if (so1 < so2) return so2; return so1; } double _getMax(double so1 , double so2) { if (so1 < so2) return so2; return so1; } PS _getMax(PS so1 , PS so2) { if (so1 < so2) return so2; return so1; } Giới Thiệu Lập Trình 4Template – Giới Thiệu 18 template T _getMax ( T so1 , T so2 ) { if ( so1 < so2 ) return so2; return so1; } int main() { PS ps1 , ps2 , psMax; psMax = _getMax ( ps1 , ps2 ) ; } Giới Thiệu Lập Trình
File đính kèm:
- bai_giang_gioi_thieu_lap_trinh_gioi_thieu_le_nguyen_khoi.pdf