Cấu trúc dữ liệu và giải thuật (Data Structure and Algorithms): Giải thuật tiệm cận - Asymptotic Algorithms tài liệu, gi...
NGUYỄN VĂN LINH TRẦN CAO ĐỆ TRƯƠNG THỊ THANH TUYỀN LÂM HOÀI BẢO PHAN HUY CƯỜNG TRẦN NGÂN BÌNH CẤU TRÚC DỮ LIỆU Trang 1 Cấu trúc dữ liệu Lời nói đầu ĐẠI HỌC CẦN THƠ – 12/2003 LỜI NÓI ĐẦU Để đáp ứng nhu cầu học tập của các bạn sinh viên, nhất là sinh viên chuyên ngành tin học, Khoa Công Nghệ Thông Tin Trường Đại Học Cần Thơ chúng tôi đã tiến hành biên soạn các giáo trình, bài giảng chính trong chương trình học. Giáo trình môn Cấu Trúc Dữ Liệu này được biên soạn cơ bản dựa trên quyển "Data Structures and Algorithms" của Alfred V. Aho, John E. Hopcroft và Jeffrey D. Ullman do Addison-Wesley tái bản năm 1987. Giáo trình này cũng được biên soạn dựa trên kinh nghiệm giảng dạy nhiều năm môn Cấu Trúc Dữ Liệu và Giải Thuật của chúng tôi. Tài liệu này được soạn theo đề cương chi tiết môn Cấu Trúc Dữ Liệu của sinh viên chuyên ngành tin học của Khoa Công Nghệ Thông Tin Trường Đại Học Cần Thơ. Mục tiêu của nó nhằm giúp các bạn sinh viên chuyên ngành có một tài liệu cô đọng dùng làm tài liệu học tập, nhưng chúng tôi cũng không loại trừ toàn bộ các đối tượng khác tham khảo. Chúng tôi nghĩ rằng các bạn sinh viên không chuyên tin và những người quan tâm tới cấu trúc dữ liệu và giải thuật sẽ tìm được trong này những điều hữu ích. Mặc dù đã rất cố gắng nhiều trong quá trình biên soạn giáo trình nhưng chắc chắn giáo trình sẽ còn nhiều thiếu sót và hạn chế. Rất mong nhận được sự đóng góp ý kiến quý báu của sinh viên và các bạn đọc để giáo trình ngày một hoàn thiện hơn. Cần thơ, ngày 10 tháng 11 năm 2003 Các tác giả Trần Cao Đệ Nguyễn Văn Linh Trương Thị Thanh Tuyền Lâm Hoài Bảo Phan Huy Cường Trần Ngân Bình Trang 2 Cấu trúc dữ liệu Mục lục MỤC LỤC CHƯƠNG I MỞ ĐẦU 9 UI. TỪ BÀI TOÁN ĐẾN CHƯƠNG TRÌNH .9 1. Mô hình hóa bài toán thực tế 9 2. Giải thuật (algorithms) .12 3. Ngôn ngữ giả và tinh chế từng bước (Pseudo-language and stepwise refinement) .15 4. Tóm tắt 17 II. KIỂU DỮ LIỆU TRỪU TƯỢNG (ABSTRACT DATA TYPE) 18 1. Khái niệm trừu tượng hóa .18 2. Trừu tượng hóa chương trình .18 3. Trừu tượng hóa dữ liệu .19 III. KIỂU DỮ LIỆU - CẤU TRÚC DỮ LIỆU VÀ KIỂU DỮ LIỆU TRỪU TƯỢNG (DATA TYPES, DATA STRUCTURES, ABSTRACT DATA TYPES) 20 CHƯƠNG II CÁC KIỂU DỮ LIỆU TRỪU TƯỢNG CƠ BẢN .22 (BASIC ABSTRACT DATA TYPES) 22 I. KIỂU DỮ LIỆU TRỪU TƯỢNG DANH SÁCH (LIST) .24 1. Khái niệm danh sách 24 2. Các phép toán trên danh sách Giải thuật tiệm cận - Asymptotic Algorithms Phân tích tiệm cận Cấu trúc liệu Giải thuật Phân tích tiệm cận gì? Phân tích tiệm cận giải thuật khái niệm giúp ước lượng thời gian chạy (Running Time) giải thuật Sử dụng phân tích tiệm cận, đưa kết luận tốt tình trường hợp tốt nhất, trường hợp trung bình, trường hợp xấu giải thuật Để tham khảo trường hợp này, bạn tìm hiểu chương Cấu trúc liệu gì? Phân tích tiệm cận tức tiệm cận liệu đầu vào (Input), tức giải thuật Input kết luận cuỗi giải thuật chạy lượng thời gian cụ thể số Ngoài nhân tố Input, nhân tố khác xem không đổi Phân tích tiệm cận nói đến việc ước lượng thời gian chạy phép tính bước tính toán Ví dụ, thời gian chạy phép tính ước lượng hàm f(n) với phép tính khác hàm g(n2) Điều có nghĩa thời gian chạy phép tính tăng tuyến tính với tăng lên n thời gian chạy phép tính thứ hai tăng theo hàm mũ n tăng lên Tương tự, n nhỏ thời gian chạy hai phép tính gần Thường thời gian cần thiết giải thuật chia thành loại: Trường hợp tốt nhất: thời gian nhỏ cần thiết để thực thi chương trình Trường hợp trung bình: thời gian trung bình cần thiết để thực thi chương trình Trường hợp xấu nhất: thời gian tối đa cần thiết để thực thi chương trình Asymptotic Notation Cấu trúc liệu giải thuật Dưới Asymptotic Notation sử dụng phổ biến việc ước lượng độ phức tạp thời gian chạy giải thuật: Ο Notation Ω Notation θ Notation Big Oh Notation, Ο Cấu trúc liệu giải thuật Ο(n) cách để biểu diễn tiệm cận thời gian chạy thuật toán Nó ước lượng độ phức tạp thời gian trường hợp xấu lượng thời gian dài cần thiết giải thuật (thực thi từ bắt đầu kết thúc) Đồ thị biểu diễn sau: Ví dụ, gọi f(n) g(n) hàm không giảm định nghĩa số nguyên dương (tất hàm thời gian thỏa mãn điều kiện này): Ο(f(n)) = { g(n) : tồn c > n0 cho g(n) ≤ c.f(n) với n > n0 } Omega Notation, Ω Cấu trúc liệu giải thuật The Ω(n) cách để biểu diễn tiệm cận thời gian chạy giải thuật Nó ước lượng độ phức tạp thời gian trường hợp tốt lượng thời gian ngắn cần thiết giải thuật Đồ thị biểu diễn sau: Ví dụ, với hàm f(n): Ω(f(n)) ≥ { g(n) : tồn c > n0 cho g(n) ≤ c.f(n) với n > n0 } Theta Notation, θ Cấu trúc liệu giải thuật The θ(n) cách để biểu diễn tiệm cận tiệm cận thời gian chạy giải thuật Bạn nhìn vào đồ sau: θ(f(n)) = { g(n) g(n) = Ο(f(n)) g(n) = Ω(f(n)) với n > n0 } Một số Asymptotic Notation phổ biến cấu trúc liệu giải thuật số − Ο(1) logarit − Ο(log n) Tuyến tính (Linear) − Ο(n) n log n − Ο(n log n) Bậc hai (Quadratic) − Ο(n2) Bậc (cubic) − Ο(n3) Đa thức (polynomial) − nΟ(1) Hàm mũ (exponential) − 2Ο(n) Mục lục Giáo trình Cấu trúc dữ liệu và Giải thuật iMỤC LỤC Phần 1 – PHẦN MƠÛ ĐẦU Chương 1 – GIỚI THIỆU 1.1. Về phương pháp phân tích thiết kế hướng đối tượng .1 1.2. Giới thiệu môn học Cấu trúc dữ liệu (CTDL) và giải thuật .1 1.3. Cách tiếp cận trong quá trình tìm hiểu các lớp CTDL 4 1.3.1. Các bước trong quá trình phân tích thiết kế hướng đối tượng .4 1.3.2. Quá trình xây dựng các lớp CTDL 5 1.4. Một số đònh nghóa cơ bản .6 1.4.1. Đònh nghóa kiểu dữ liệu .6 1.4.2. Kiểu nguyên tố và các kiểu có cấu trúc .6 1.4.3. Chuỗi nối tiếp và danh sách 6 1.4.4. Các kiểu dữ liệu trừu tượng 7 1.5. Một số nguyên tắc và phương pháp để học tốt môn CTDL và giải thuật 8 1.5.1. Cách tiếp cận và phương hướng suy nghó tích cực 8 1.5.2. Các nguyên tắc 9 1.5.3. Phong cách lập trình (style of programming) và các kỹ năng: .10 1.6. Giới thiệu về ngôn ngữ giả: 14 Phần 2 – CÁC CẤU TRÚC DỮ LIỆU Chương 2 – NGĂN XẾP 2.1. Đònh nghóa ngăn xếp .17 2.2. Đặc tả ngăn xếp .18 2.3. Các phương án hiện thực ngăn xếp 22 2.4. Hiện thực ngăn xếp .22 2.4.1. Hiện thực ngăn xếp liên tục 22 2.4.2. Hiện thực ngăn xếp liên kết 25 2.4.3. Ngăn xếp liên kết với sự an toàn 29 2.4.4. Đặc tả ngăn xếp liên kết đã hiệu chỉnh .34 Mục lục Giáo trình Cấu trúc dữ liệu và Giải thuật ii Chương 3 – HÀNG ĐI 3.1. Đònh nghóa hàng . 37 3.2. Đặc tả hàng . 38 3.3. Các phương án hiện thực hàng 41 3.3.1. Các phương án hiện thực hàng liên tục . 41 3.3.2. Phương án hiện thực hàng liên kết 45 3.4. Hiện thực hàng 46 3.4.1. Hiện thực hàng liên tục . 46 3.4.2. Hiện thực hàng liên kết 48 3.4.3. Hàng liên kết mở rộng 50 Chương 4 – DANH SÁCH 4.1. Đònh nghóa danh sách 51 4.2. Đặc tả các phương thức cho danh sách . 51 4.3. Hiện thực danh sách . 54 4.3.1. Hiện thực danh sách liên tục 54 4.3.2. Hiện thực danh sách liên kết đơn giản . 56 4.3.3. Lưu lại vò trí hiện tại . 61 4.3.4. Danh sách liên kết kép . 63 4.4. So sánh các cách hiện thực của danh sách . 66 4.5. Danh sách liên kết trong mảng liên tục . 67 4.5.1. Phương pháp . 67 4.5.2. Các tác vụ quản lý vùng nhớ . 70 4.5.3. Các tác vụ khác CẤU TRÚC DỮ LIỆU VÀ GIẢI THUẬT DATA STRUCTURE AND ALGORITHMS GV: Phạm Tuấn Hiệp Email: hiep0109@yahoo.com Ôn tập tốt nghiệp Nội dung ôn tập Chương 1: Ôn tập Kỹ thuật lập trình Chương 2: Tìm kiếm, Sắp xếp Chương 3: Danh sách liên kết Chương 4: Cây 2 Ôn tập tốt nghiệp Tài liệu học tập Giáo trình: C & Data Structures, P. S. Deshpande, O. G. Kakde - CHARLES RIVER MEDIA, INC. Hingham, Massachusetts. Tham khảo: Giáo trình Cấu trúc dữ liệu 1, Trần Hạnh Nhi – Dương Anh Đức, Trường ĐHKHTN – ĐHQG TP.HCM. Phần mềm lập trình: C-Free 4.0 Borland C++ … 3 Chương 1: Ôn tập Kỹ thuật lập trình 4 Ôn tập tốt nghiệp Nội dung Con trỏ Mảng 1 chiều Đệ quy 5 Ôn tập tốt nghiệp Con trỏ Cách khai báo con trỏ Các phép toán trên con trỏ 6 void main(){ int x=10, y=20; int *p, *q; p=&x; q=&y; cout<<x<<" "<<y<<endl; cout<<*p<<" "<<*q<<end; } Cho biết kết quả in ra màn hình? x = 10 y = 10 p = 10 q = 10 Ôn tập tốt nghiệp Con trỏ void main(){ int x=10, y=20; int *p, *q; p=&x; q=&y; *p=50; *q=90; cout<<x<<" "<<y<<endl; cout<<*p<<" "<<*q<<end; } Cho biết kết quả in ra màn hình? 7 x = 50 y = 90 p = 50 q = 90 Ôn tập tốt nghiệp Con trỏ void main(){ int x=10, y=20; int *p, *q; p=&x; q=&y; *p=50; *q=90; p=q; cout<<x<<" "<<y<<endl; cout<<*p<<" "<<*q<<end; } Cho biết kết quả in ra màn hình? 8 x = 50 y = 90 p = 90 q = 90 Ôn tập tốt nghiệp Con trỏ Cho biết kết quả của chương trình sau: int Test(int &a, int b, int &c) { a ; a+=b; ++c=a+b; return a+b+c; } int x=5, y=2, z=2011; void main(){ cout<<Test(x,y,z)<<" "<<x<<" "<<y<<" "<<z<<endl; } 9 A. 16 6 2 2011 B. 16 5 2 8 C. 16 5 2 2011 D. 16 6 2 8 Ôn tập tốt nghiệp Nội dung Con trỏ Mảng 1 chiều Đệ quy 10 Ôn tập tốt nghiệp Mảng 1 chiều Khai báo mảng Các phép toán trên mảng 11 void function(char *s1, char *s2){ while (*(s1++)=*(s2++)); } void main(){ char s2[100]; char s1[]="Giao Trinh Ngon Ngu C++"; function(s2,s1); cout<<s2; } Cho biết kết quả in ra màn hình? Giao Trinh Ngon Ngu C++ Ôn tập tốt nghiệp Mảng 1 chiều void main(){ float a[5]={5, 4, 3, 2, 1}; float x; int i; for(i=0; i<5; i++) a[i] += a[0]; x=a[1]+a[4]; cout<<x; } Cho biết kết quả in ra màn hình? 12 A. 125 B. 5 C. 100 D. 25 Ôn tập tốt nghiệp Mảng 1 chiều Cho biết kết quả của chương trình sau: void main(){ int a[]={5,1,12,11,8,20,14,12,7}; for(int i=4;i<=7;i++) for(int j=i+1;j<=8;j++) if(a[i]>a[j]){ int t=a[i]; a[i]=a[j]; a[j]=t; } cout<<a[6]; } 13 A. 7 B. 12 C. 8 D. 20 Ôn tập tốt nghiệp Nội dung Con trỏ Mảng 1 chiều Đệ quy 14 Ôn tập tốt nghiệp Đệ quy Đệ quy là sự gọi lại chính nó khi thực hiện Thường được dùng cho các bài toán truy hồi 15 Cho hàm đệ quy sau: int Func(int n){ if(n == 5) return 5; else return 2 * Func(n+1); } Giá trị của Func(2) là? A. 50 B. 2 C. 5 D. 40 Ôn tập tốt nghiệp Đệ quy void Foo(int x){ if(x>0) Foo(x-3); cout<<x<<" "; } Cho biết kết quả in ra màn hình khi goi hàm Foo(6)? 16 A. 6 3 B. 0 3 6 C. 0 3 D. 6 3 0 Chương 2: Tìm kiếm, Sắp xếp 17 Ôn tập tốt nghiệp Nội dung Tìm kiếm tuyến tính, nhị phân Các thuật toán sắp xếp Đổi chỗ trực tiếp (Interchange sort) Nổi bọt (Bubble sort) Chèn trực tiếp (Insertion sort) Chọn trực tiếp (Selection sort) Dựa trên phân hoạch (Quick sort) 18 Ôn tập tốt nghiệp Tìm kiếm CấU TRÚC Dữ LIệU VÀ GIảI THUẬT DATA STRUCTURE AND ALGORITHMS 1 Chương 1: Ôn tập C/C++ Chương 1: Ôn tập C/C++ Nội dung môn học Chương 0: Giới thiệu chung về CTDL và GT Chương 1: Ôn tập C/C++ Chương 2: Đệ quy (Recursion) Chương 3: Tìm kiếm (Searching) Chương 4: Sắp xếp (Sorting) Chương 5: Ngăn xếp - Hàng đợi (Stacks - Queues) Chương 6: Danh sách liên kết (Linked List) Chương 7: Cây (Tree) 2 Chương 1: Ôn tập C/C++ Chương 1: Ôn tập C/C++ Đánh giá kết quả 1. Kiểm tra giữa kỳ: thực hành Điểm Kiểm tra giữa kỳ < 4 không được thi kết thúc môn học lại 2. Kiểm tra cuối kỳ: thực hành Điểm Kiểm tra cuối kỳ < 5 không được thi kết thúc môn học lại 3. Bài tập lớn: làm các bài tập trong module Điểm Đề tài < 5 không được thi kết thúc môn học lại 4. Thi kết thúc môn: trắc nghiệm 5. Kiểm tra thường kỳ 3 Chương 1: Ôn tập C/C++ Chương 1: Ôn tập C/C++ Tài liệu học tập Giáo trình: C & Data Structures, P. S. Deshpande, O. G. Kakde - CHARLES RIVER MEDIA, INC. Hingham, Massachusetts. Tham khảo: Giáo trình Cấu trúc dữ liệu 1, Trần Hạnh Nhi – Dương Anh Đức, Trường ĐHKHTN – ĐHQG TP.HCM. Phần mềm lập trình: C-Free Borland C++ … 4 Chương 1: Ôn tập C/C++ Chương 1: Ôn tập C/C++ Nhắc nhở một số quy định Đi học đúng giờ Đeo thẻ SV Không để chuông điện thoại reo trong giờ học Không nghe điện thoại, nhắn tin trong giờ học Không nói chuyện riêng, làm ồn khi nghe giảng Mang đầy đủ tài liệu học tập của môn học (khi học LT và TH): giáo trình, bài tập, tập chép bài (hoặc slide bài giảng), usb để lưu bài tập Phải làm bài tập ở nhà Nếu vi phạm: Nhắc nhở chung Bị mời ra khỏi lớp Xóa tên khỏi môn học 5 Chương 0: Giới thiệu chung 6 Chương 1: Ôn tập C/C++ Chương 1: Ôn tập C/C++ Nội dung Cấu trúc dữ liệu Thuật toán Độ phức tạp của thuật toán 7 Chương 1: Ôn tập C/C++ Chương 1: Ôn tập C/C++ Cấu trúc dữ liệu (1) Sự tổ chức hợp lý của các thành phần dữ liệu, (2) Tập các thao tác để truy cập các thành phần dữ liệu. Ví dụ: Mảng (Array) Danh sách liên kết (Linked List) Ngăn xếp (Stack) Hàng đợi (Queue) Cây (Tree) … (1) the logical arrangement of data elements, combined with (2) the set of operations we need to access the elements. 8 Chương 1: Ôn tập C/C++ Chương 1: Ôn tập C/C++ Nội dung Cấu trúc dữ liệu Thuật toán Độ phức tạp của thuật toán 9 Chương 1: Ôn tập C/C++ Chương 1: Ôn tập C/C++ Thuật toán Tập các bước có thể tính toán được để đạt được kết quả mong muốn (A computable set of steps to achieve a desired result) Ví dụ: Tính tổng các số nguyên lẻ từ 1 n B1: S=0 B2: i=1 B3: Nếu i>n thì sang B7, ngược lại sang B4 B4: S=S+i B5: i=i+2 B6: Quay lại B3 B7: Tổng cần tìm là S 10 [...]... của CTDL và thuật toán 11 CTDL + Thuật toán = Chương trình Chương 1: Ôn tập Nội dung 12 Cấu trúc dữ liệu Thuật toán Độ phức tạp của thuật toán (algorithm complexity) Chương 1: Ôn tập Thời gian thực Cấu trúc liệu giải thuật (Data Structure and Algorithms): Cấu trúc liệu mảng Cấu trúc liệu mảng Cấu trúc liệu mảng gì? Mảng (Array) cấu trúc liệu cũ quan trọng Mảng lưu giữ số phần tử cố định phần tử có kiểu Hầu hết cấu trúc liệu sử dụng mảng để triển khai giải thuật Dưới khái niệm quan trọng liên quan tới Mảng • Phần tử: Mỗi mục lưu giữ mảng gọi phần tử • Chỉ mục (Index): Mỗi vị trí phần tử mảng có mục số sử dụng để nhận diện phần tử Mảng gồm ghi có kiểu giống nhau, có kích thước cố định, phần tử xác định số Mảng cấu trúc liệu cấp phát lien tục Ưu điểm mảng: • Truy câp phần tử với thời gian số O(1) • Sử dụng nhớ hiệu • Tính cục nhớ Nhược điểm • Không thể thay đổi kích thước mảng chương trình dang thực Mảng động Mảng động (dynamic aray): cấp phát nhớ cho mảng cách động trình chạy chương trình C malloc calloc, C++ new Sử dụng mảng động ta bắt đầu với mảng có phàn tử, số lượng phàn tử vượt qua khả ảng ta gấp đôi kích thước mảng cuc copy phàn tử mảng cũ vào nửa đầu mảng Ưu điểm: tránh lãng phí nhớ phải khai báo mảng có kích thước lớn từ đầu Nhược điểm: + phải thực them thao tác copy phần tử thay đổi kích thước + số thời gian thực thao tác không số Biểu diễn Cấu trúc liệu mảng Mảng khai báo theo nhiều cách đa dạng ngôn ngữ lập trình Để minh họa, sử dụng phép khai báo mảng ngôn ngữ C: Hình minh họa phần tử mục: Dưới số điểm cần ghi nhớ cấu trúc liệu mảng: • Chỉ mục bắt đầu với • Độ dài mảng 10, nghĩa mảng lưu giữ 10 phần tử • Mỗi phần tử truy cập thông qua mục phần tử Ví dụ, lấy giá trị phần tử mục 27 Phép toán hỗ trợ mảng Dưới hoạt động hỗ trợ mảng: • Duyệt: In tất phần tử mảng theo cách in phần tử • Chèn: Thêm phần tử vào mảng mục cho • Xóa: Xóa phần tử từ mảng mục cho • Tìm kiếm: Tìm kiếm phần tử sử dụng mục hay giá trị • Cập nhật: Cập nhật giá trị phần tử mục Trong ngôn ngữ C, mảng khởi tạo với kích cỡ ban đầu, gán giá trị mặc định cho phần tử mảng theo thứ tự sau: Kiểu liệu Giá trị mặc định bool false char int float 0.0 double 0.0f void wchar_t Hoạt động chèn phần tử vào mảng Hoạt động chèn để chèn nhiều phần tử liệu vào mảng Tùy theo yêu cầu, phần tử chèn vào vị trí đầu, vị trí cuối vị trí mục cho mảng Phần triển khai hoạt động chèn ví dụ thực Trong ví dụ này, chèn liệu vào cuối mảng Ví dụ Giả sử LA mảng tuyến tính thứ tự có N phần tử K số nguyên dương thỏa mãn K = K Gán LA[J+1] = LA[J] Gán J = J-1 Gán LA[K] = ITEM Kết thúc Sau code đầy đủ giải thuật ngôn ngữ C: #include main() { int LA[] = {1,3,5,7,8}; int item = 10, k = 3, n = 5; int i = 0, j = n; printf("Danh sach phan tu mang ban dau:\n"); for(i = 0; i= k){ LA[j+1] = LA[j]; j = j - 1; } LA[k] = item; printf("Danh sach phan tu cua mang sau hoat dong chen:\n"); for(i = 0; i ... Notation, θ Cấu trúc liệu giải thuật The θ(n) cách để biểu diễn tiệm cận tiệm cận thời gian chạy giải thuật Bạn nhìn vào đồ sau: θ(f(n)) = { g(n) g(n) = Ο(f(n)) g(n) = Ω(f(n)) với n > n0 } Một số Asymptotic. .. Notation, Ω Cấu trúc liệu giải thuật The Ω(n) cách để biểu diễn tiệm cận thời gian chạy giải thuật Nó ước lượng độ phức tạp thời gian trường hợp tốt lượng thời gian ngắn cần thiết giải thuật Đồ... { g(n) g(n) = Ο(f(n)) g(n) = Ω(f(n)) với n > n0 } Một số Asymptotic Notation phổ biến cấu trúc liệu giải thuật số − Ο(1) logarit − Ο(log n) Tuyến tính (Linear) − Ο(n) n log n − Ο(n log n) Bậc