You are on page 1of 19

Võ Tiến

Cấu trúc dữ liệu và giải thuật


Thí Nghiệm (Lab)
nội dung

nhóm thảo luận CSE


https://www.facebook.com/groups/211867931379013

Tp. Hồ Chí Minh, Tháng 2/2024

https://www.facebook.com/groups/211867931379013 Trang 1/19


Nhóm thảo luận CSE
Võ Tiến

Mục lục
1 Lab 3 - Sort 3
1.1 Sort . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3
1.1.1 Câu 1 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3
1.1.2 Câu 2 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 7
1.1.3 Câu 3 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9
1.1.4 Câu 4 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11
1.1.5 Câu 5 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 13
1.1.6 Câu 6 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 16

2 Các Khóa Học HK232 19

https://www.facebook.com/groups/211867931379013 Trang 2/19


Nhóm thảo luận CSE
Võ Tiến

1 Lab 3 - Sort
1.1 Sort
1.1.1 Câu 1

Hình 1: ảnh câu hỏi

https://www.facebook.com/groups/211867931379013 Trang 3/19


Nhóm thảo luận CSE
Võ Tiến

Hình 2: ảnh câu hỏi

2 #include <iostream>
3 #include <sstream>
4 using namespace std;
5

6 template <class T>


7 class SLinkedList {
8 public:
9 class Node; // Forward declaration
10 protected:
11 Node* head;
12 Node* tail;
13 int count;
14 public:
15 SLinkedList()
16 {
17 this->head = nullptr;
18 this->tail = nullptr;

https://www.facebook.com/groups/211867931379013 Trang 4/19


Nhóm thảo luận CSE
Võ Tiến

19 this->count = 0;
20 }
21 ~SLinkedList(){};
22 void add(T e)
23 {
24 Node *pNew = new Node(e);
25

26 if (this->count == 0)
27 {
28 this->head = this->tail = pNew;
29 }
30 else
31 {
32 this->tail->next = pNew;
33 this->tail = pNew;
34 }
35

36 this->count++;
37 }
38 int size()
39 {
40 return this->count;
41 }
42 void printList()
43 {
44 stringstream ss;
45 ss << "[";
46 Node *ptr = head;
47 while (ptr != tail)
48 {
49 ss << ptr->data << ",";
50 ptr = ptr->next;
51 }
52

53 if (count > 0)
54 ss << ptr->data << "]";
55 else
56 ss << "]";
57 cout << ss.str() << endl;
58 }
59 public:
60 class Node {
61 private:
62 T data;
63 Node* next;
64 friend class SLinkedList<T>;
65 public:
66 Node() {
67 next = 0;
68 }
69 Node(T data) {
70 this->data = data;
71 this->next = nullptr;
72 }
73 };
74

https://www.facebook.com/groups/211867931379013 Trang 5/19


Nhóm thảo luận CSE
Võ Tiến

75 void bubbleSort();
76 };
77

78 template <class T>


79 void SLinkedList<T>::bubbleSort()
80 {
81 //! Khởi đầu, nếu linked list rỗng thì return
82 if(head == NULL) return;
83

84 //! Khởi tạo hai node i và j để duyệt linked list


85 Node* i = head;
86 while(i->next){
87 Node* j = head;
88 while(j->next){
89 //! Nếu giá trị của node j lớn hơn giá trị của node liền sau nó thì swap hai node đó
90 if(j->data > j->next->data){
91 swap(j->data,j->next->data);
92 }
93 j = j ->next;
94 }
95 //! In ra linked list hiện tại
96

97 this->printList();
98 i = i->next;
99 }
100 }
101

102 int main(){


103 int arr[] = {9, 2, 8, 4, 1};
104 SLinkedList<int> list;
105 for(int i = 0; i <int(sizeof(arr))/4;i++)
106 list.add(arr[i]);
107 list.bubbleSort();
108 /*
109 *[2,8,4,1,9]
110 *[2,4,1,8,9]
111 *[2,1,4,8,9]
112 *[1,2,4,8,9]
113 */
114 }

https://www.facebook.com/groups/211867931379013 Trang 6/19


Nhóm thảo luận CSE
Võ Tiến

1.1.2 Câu 2

Hình 3: ảnh câu hỏi

2 #include <iostream>
3 using namespace std;
4

5 template <class T>


6 class Sorting
7 {
8 public:
9 /* Function to print an array */
10 static void printArray(T *start, T *end)
11 {
12 int size = end - start;
13 for (int i = 0; i < size - 1; i++)
14 cout << start[i] << ", ";
15 cout << start[size - 1];
16 cout << endl;
17 }
18

19 static void selectionSort(T *start, T *end);


20 };
21

22 template <class T>


23 void Sorting<T>::selectionSort(T *start, T *end)
24 {
25 T* result = start;
26 while(start != end - 1){
27 //! Con trỏ min trỏ đến phần tử nhỏ nhất trong phạm vi chưa sắp xếp

https://www.facebook.com/groups/211867931379013 Trang 7/19


Nhóm thảo luận CSE
Võ Tiến

28 T* min = start;
29 //! Con trỏ tmp dùng để duyệt qua các phần tử còn lại
30 T* tmp = start + 1;
31 while(tmp != end){
32 //! Nếu phần tử tại tmp nhỏ hơn phần tử nhỏ nhất hiện tại, cập nhật min
33 if(*tmp < * min){
34 min = tmp;
35 }
36 tmp++;
37 }
38 //! Hoán đổi phần tử nhỏ nhất tìm được với phần tử đầu tiên trong phạm vi chưa sắp
↪ xếp
39 swap(*start, *min);
40 //! in ra phần tử
41 Sorting<T>::printArray(result,end);
42 start++;
43

44 }
45 }
46

47 int main(){
48 int arr[] = {9, 2, 8, 1, 0, -2};
49 Sorting<int>::selectionSort(&arr[0], &arr[6]);
50 /*
51 *-2, 0, 8, 1, 2, 9
52 *-2, 0, 1, 8, 2, 9
53 *-2, 0, 1, 2, 8, 9
54 *-2, 0, 1, 2, 8, 9
55

56 */
57 }

https://www.facebook.com/groups/211867931379013 Trang 8/19


Nhóm thảo luận CSE
Võ Tiến

1.1.3 Câu 3

Hình 4: ảnh câu hỏi

1 #include <sstream>
2 #include <iostream>
3 #include <type_traits>
4 using namespace std;
5

6 template <class T>


7 class Sorting {
8 private:
9 static void printArray(T* start, T* end)
10 {
11 int size = end - start;
12 for (int i = 0; i < size; i++)
13 cout << start[i] << " ";
14

15 cout << endl;


16 }
17

18 public:
19 // TODO: Write your code here
20 static void sortSegment(T* start, T* end, int segment_idx, int
↪ cur_segment_total);
21 static void ShellSort(T* start, T* end, int* num_segment_list, int num_phases);
22 };
23

24 template <class T>


25 // !Hàm sortSegment thực hiện sắp xếp một đoạn (segment) của mảng bằng phương pháp
↪ insertion sort

https://www.facebook.com/groups/211867931379013 Trang 9/19


Nhóm thảo luận CSE
Võ Tiến

26 void Sorting<T>::sortSegment(T* start, T* end, int segment_idx, int


↪ cur_segment_total) {
27

28 //! Con trỏ left trỏ vào phần tử bắt đầu của segment hiện tại
29 T* left = start + segment_idx;
30

31 while(left <= end - cur_segment_total){


32 //! Con trỏ tmp dùng để duyệt qua các phần tử trong segment
33 T* tmp = start + segment_idx;
34

35 while(tmp <= end - cur_segment_total - 1){


36 //! So sánh phần tử hiện tại với phần tử cách cur_segment_total vị trí sau
37 if(* tmp > * (tmp + cur_segment_total)) swap(*tmp,* (tmp +
↪ cur_segment_total));
38 //! Di chuyển tmp đến phần tử tiếp theo cách cur_segment_total vị trí
39 tmp += cur_segment_total;
40

41 }
42 //! Di chuyển left đến phần tử bắt đầu của segment tiếp theo
43 left += cur_segment_total;
44

45 }
46

47 }
48

49 template <class T>


50 //! Hàm ShellSort thực hiện thuật toán Shell sort trên mảng từ start đến end
51 void Sorting<T>::ShellSort(T* start, T* end, int* num_segment_list, int
↪ num_phases) {
52

53 //! Duyệt qua các pha sắp xếp theo danh sách độ dài segment đã cho
54 for(int i = num_phases-1; i >= 0; i--){
55 //! Duyệt qua các segment trong pha hiện tại
56 for(int j = 0; j < num_segment_list[i];j ++ ){
57

58 //! Sắp xếp từng segment


59

60 sortSegment(start, end,j , num_segment_list[i]);


61

62 }
63 cout << num_segment_list[i] << " segments: ";
64 T* tmp = start;
65 Sorting<T>::printArray(start,end);
66 }
67

68 }
69

70 int main(){
71

72 int num_segment_list[] = {1, 3, 5};


73 int num_phases = 2;
74 int array[] = { 10, 9, 8 , 7 , 6, 5, 4, 3, 2, 1 };
75

76 Sorting<int>::ShellSort(&array[0], &array[10], &num_segment_list[0], num_phases);


77 //!5 segments: 5 4 3 2 1 10 9 8 7 6
78 //!3 segments: 2 1 3 5 4 7 6 8 10 9

https://www.facebook.com/groups/211867931379013 Trang 10/19


Nhóm thảo luận CSE
Võ Tiến

79 //!1 segments: 1 2 3 4 5 6 7 8 9 10
80 }

1.1.4 Câu 4

Hình 5: ảnh câu hỏi

1 #include <sstream>
2 #include <iostream>
3 #include <type_traits>
4

5 using namespace std;


6

7 template <class T>


8 class Sorting {
9 private:

https://www.facebook.com/groups/211867931379013 Trang 11/19


Nhóm thảo luận CSE
Võ Tiến

10 static T* Partition(T* start, T* end) ;


11 public:
12 static void QuickSort(T* start, T* end) ;
13 };
14

15 template <class T>


16 T* Sorting<T>::Partition(T* start, T* end) {
17 T* arr = start;
18 int low = 0, high = end - start - 1;
19 int pivot = arr[low];
20 int i = low, j = high + 1;
21

22 do {
23 // Find leftmost element greater than
24 // or equal to pivot
25 //! Tìm phần tử bên trái đầu tiên lớn hơn hoặc bằng pivot
26 do {
27 i++;
28 } while (arr[i] < pivot);
29

30 // Find rightmost element smaller than


31 // or equal to pivot
32 //! Tìm phần tử bên phải đầu tiên nhỏ hơn hoặc bằng pivot
33 do {
34 j--;
35 } while (arr[j] > pivot);
36

37 // If two pointers met.


38 if (i >= j){
39 break;
40 }
41 //! Đổi chỗ hai phần tử không đúng thứ tự
42 swap(arr[i], arr[j]);
43 } while(i <= j);
44 //! Đưa pivot vào vị trí đúng trong mảng con bên trái.
45 if(i <= j) swap(arr[i], arr[j]);
46 swap(arr[low], arr[j]);
47 cout << j << " ";
48 return start + j;
49 }
50 template <class T>
51 void Sorting<T>::QuickSort(T* start, T* end) {
52 if(start < end){
53 T* privot = Partition(start, end);
54 QuickSort(start, privot);
55 QuickSort(privot+1,end);
56 }
57 }
58

59 int main(){
60 int array[] = { 3, 5, 7, 10 ,12, 14, 15, 13, 1, 2, 9, 6, 4, 8, 11, 16, 17, 18,
↪ 20, 19 };
61 cout << "Index of pivots: ";
62 Sorting<int>::QuickSort(&array[0], &array[20]);
63 cout << "\n";
64 cout << "Array after sorting: ";

https://www.facebook.com/groups/211867931379013 Trang 12/19


Nhóm thảo luận CSE
Võ Tiến

65 for (int i : array) cout << i << " ";


66 }

1.1.5 Câu 5

Hình 6: ảnh câu hỏi

2 #include <iostream>
3 using namespace std;
4 template <class T>
5 class Sorting {
6 public:
7 /* Function to print an array */
8 static void printArray(T *start, T *end)
9 {
10 long size = end - start + 1;
11 for (int i = 0; i < size - 1; i++)
12 cout << start[i] << ", ";
13 cout << start[size - 1];
14 cout << endl;
15 }
16

17 static void merge(T* left, T* middle, T* right);


18 static void mergeSort(T* start, T* end) ;
19 };
20 template <class T>

https://www.facebook.com/groups/211867931379013 Trang 13/19


Nhóm thảo luận CSE
Võ Tiến

21 void Sorting<T>::merge(T* left, T* middle, T* right){


22

23 //! Khai báo mảng tạm thời


24 T* arr = left;
25 int l = 0, m = middle - left, r = right - left;
26 //! Kích thước mảng con thứ nhất
27 int n1 = m - l + 1;
28 //! Kích thước mảng con thứ hai
29 int n2 = r - m;
30

31 // Create temp arrays


32 //! Tạo mảng tạm thời
33 int L[n1], R[n2];
34

35 //* Copy data to temp arrays L[] and R[]


36 //! Sao chép dữ liệu vào mảng tạm thời L[] và R[]
37 for(int i = 0; i < n1; i++)
38 L[i] = arr[l + i];
39 for(int j = 0; j < n2; j++)
40 R[j] = arr[m + 1 + j];
41

42 // Merge the temp arrays back into arr[l..r]


43 int i = 0;
44 //* Initial index of second subarray
45

46 int j = 0;
47

48 //* Initial index of merged subarray


49 int k = l;
50

51 while (i < n1 && j < n2)


52 {
53 if (L[i] <= R[j])
54 {
55 arr[k] = L[i];
56 i++;
57 }
58 else
59 {
60 arr[k] = R[j];
61 j++;
62 }
63 k++;
64 }
65

66 //* Copy the remaining elements of


67 //* L[], if there are any
68 while (i < n1)
69 {
70 arr[k] = L[i];
71 i++;
72 k++;
73 }
74

75 //* Copy the remaining elements of


76 //* R[], if there are any

https://www.facebook.com/groups/211867931379013 Trang 14/19


Nhóm thảo luận CSE
Võ Tiến

77 while (j < n2)


78 {
79 arr[k] = R[j];
80 j++;
81 k++;
82 }
83 printArray(left,right);
84 }
85 template <class T>
86 void Sorting<T>::mergeSort(T* start, T* end){
87 if(start < end){
88 T* mid = (end - start) / 2 + start;
89 mergeSort(start, mid);
90 mergeSort(mid+1,end);
91 merge(start, mid, end);
92 }
93 }
94

95 int main(){
96

97 int arr[] = {0,2,4,3,1,4};


98 Sorting<int>::mergeSort(&arr[0], &arr[5]);
99

100 /*
101 *0, 2
102 *0, 2, 4
103 *1, 3
104 *1, 3, 4
105 *0, 1, 2, 3, 4, 4
106 */
107 }

https://www.facebook.com/groups/211867931379013 Trang 15/19


Nhóm thảo luận CSE
Võ Tiến

1.1.6 Câu 6

Hình 7: ảnh câu hỏi

https://www.facebook.com/groups/211867931379013 Trang 16/19


Nhóm thảo luận CSE
Võ Tiến

1 #include <iostream>
2 using namespace std;
3 template <class T>
4 class Sorting {
5 public:
6 /* Function to print an array */
7 static void printArray(T *start, T *end)
8 {
9 long size = end - start + 1;
10 for (int i = 0; i < size - 1; i++)
11 cout << start[i] << ", ";
12 cout << start[size - 1];
13 cout << endl;
14 }
15

16 static void merge(T* left, T* middle, T* right);


17 static void mergeSort(T* start, T* end);
18 };
19

20

21 // You must use the nodes in the original list and must not modify ListNode's val
↪ attribute.
22 // Hint: You should complete the function mergeLists first and validate it using our
↪ first testcase example
23

24 // Merge two sorted lists


25 //! Hàm để hợp nhất hai danh sách đã sắp xếp
26 template <class T>
27 ListNode* Sorting<T>::mergeLists(ListNode* a, ListNode* b){
28 //! Nếu danh sách a rỗng, trả về danh sách b
29 if(a == NULL) return b;
30 //! Nếu danh sách b rỗng, trả về danh sách a
31 else if(b == NULL) return a;
32 //! Tạo một node mới để làm node gốc của danh sách kết quả
33 ListNode * result = new ListNode(0);
34 ListNode* tmp = result;
35 //! Lặp qua cả hai danh sách a và b
36 while(a || b){
37 if(!b || (a && a->val < b->val)){
38 tmp->next = a;
39 a = a->next;
40 tmp = tmp->next;
41 }
42 else{
43 tmp->next = b;
44 b = b->next;
45 tmp = tmp->next;
46 }
47 }
48 return result->next;
49 }
50

51 // Sort and unsorted list given its head pointer


52 //! Hàm tìm node giữa của danh sách
53 template <class T>

https://www.facebook.com/groups/211867931379013 Trang 17/19


Nhóm thảo luận CSE
Võ Tiến

54 ListNode* Sorting<T>::idnode(ListNode* a){


55 ListNode* tmp = a;
56 while(tmp->next && tmp->next->next){
57 //! Di chuyển con trỏ a đến node giữa
58 a = a->next;
59 //! Di chuyển con trỏ tmp đến node hai bước tiếp theo
60 tmp = tmp->next->next;
61 }
62 tmp = a->next; //! Lấy node sau node giữa
63 a->next = NULL; //! Cắt kết nối giữa danh sách từ node giữa
64 return tmp;
65 }
66 ListNode* mergeSortList(ListNode* head) {
67

68 if(head == NULL || head->next == NULL) return head;


69 ListNode* mid = midnode(head);
70 head = mergeSortList(head);
71 mid = mergeSortList(mid);
72 return mergeLists(head,mid);
73

74 }
75

76 int main(){
77 int arr1[] = {1, 3, 5, 7, 9};
78 int arr2[] = {2, 4, 6, 8};
79 unordered_map<ListNode*, int> nodeAddr;
80 ListNode* a = init(arr1, sizeof(arr1) / 4, nodeAddr);
81 ListNode* b = init(arr2, sizeof(arr2) / 4, nodeAddr);
82 ListNode* merged = mergeLists(a, b);
83 try {
84 printList(merged, nodeAddr);
85 }
86 catch(char const* err) {
87 cout << err << '\n';
88 }
89 freeMem(merged);
90 }

https://www.facebook.com/groups/211867931379013 Trang 18/19


Nhóm thảo luận CSE
Võ Tiến

2 Các Khóa Học HK232


Võ Tiến
https://www.facebook.com/profile.php?id=100056605580171
Các lớp HK232 sẽ mở
• Lớp BTL1 + GK (giữa kì) + LAB + Lý thuyết + Harmony của môn
DSA HK232
• Lớp BTL2 + CK (cuối kì) + LAB + Lý thuyết + Harmony của môn
DSA HK232
• Lớp BTL1 + LAB + Lý thuyết + Harmony của môn KTLT HK232
• Lớp BTL2 + LAB + Lý thuyết + Harmony + CK của môn KTLT
HK232
• Lớp BTL1 + BTL2 + GK + Harmony của môn PPL HK232
• Lớp BTL3 + BTL4 + CK + Harmony của môn PPL HK232
CHÚC CÁC EM HỌC TỐT

https://www.facebook.com/groups/211867931379013 Trang 19/19


Nhóm thảo luận CSE

You might also like