stack & queue

Post on 13-Feb-2017

97 Views

Category:

Software

0 Downloads

Preview:

Click to see full reader

TRANSCRIPT

NỘI DUNG Kiểu dữ liệu Stack & Queue Cài đặt Stack & Queue Các cơ chế an toàn Ứng dụng thực tiễn

DANH SÁCH Danh sách

Dãy hữu hạn phần tử Các thao tác: tạo mới, hủy, thêm, xóa, …

Danh sách và mảng Ví dụ minh họa

DANH SÁCH ĐẶC, DANH SÁCH LIÊN KẾT Danh sách đặc: dùng mảng cài đặt Danh sách liên kết: dùng cấu trúc liên kết So sánh về mặt sử dụng bộ nhớ So sánh về mặt thao tác

1 3 5 8 …

1 o 3 o 5 o 8 o

NULL

max_count = 100

1

DANH SÁCH HẠN CHẾ Danh sách: Thêm, xóa ở vị trí bất kỳ Stack: Thêm, xóa từ một đầu Queue: Thêm đầu này, xóa đầu kia Dùng List như Stack hoặc Queue?

3 7 9

5

1 3 7 9571 3 9

NGĂN XẾP Stack: Thêm, xóa phần tử từ một đầu (top) Stack là cấu trúc LIFO (Last In First Out)

HÀNG ĐỢI Queue: Thêm vào đầu này, lấy ra đầu kia Queue là cấu trúc FIFO (First In First Out)

1234

4

125 345

CÀI ĐẶT Danh sách đặc Danh sách liên kết

CÀI ĐẶT NGĂN XẾP BẰNGDANH SÁCH ĐẶC (Stack.h)const max_stack = 100; // kích thước tối đatemplate <class Stack_Element> // Stack_Element=int, double, string, Employee class Stack{private: // định nghĩa cấu trúc dữ liệuint count; // vị trí top, số phần tửStack_Entry entry[max_stack];public: // định nghĩa các thao tác trừu tượngStack(); // hàm khởi tạo mặc địnhbool empty() const;bool full() const;bool push(const Stack_Entry &item);bool pop();};

count

CÀI ĐẶT NGĂN XẾP BẰNGDANH SÁCH ĐẶC (Stack.cpp)template <class Stack_Element>Stack<Stack_Element>::Stack(){

count = 0;}

bool Stack<Stack_Element>::push(const Stack_Entry &item){

bool outcome = true;if full()

outcome = false;else

entry[count++] = item;return outcome;

}

count

count

item

count

item

item

CÀI ĐẶT NGĂN XẾP BẰNGDANH SÁCH ĐẶC (Stack.cpp)template <class Stack_Element>bool Stack<Stack_Element>::pop(){

bool outcome = true;if empty()

outcome = false;else

count--;return outcome;

}

count

count

count

CÀI ĐẶT NGĂN XẾP BẰNGDANH SÁCH ĐẶC (Stack.cpp)template <class Stack_Element>bool Stack<Stack_Element>::empty() const{

return (count == 0);}template <class Stack_Element>bool Stack<Stack_Element>::full() const{

return (count == max_stack);}

count

count=max_stack

.

.

.

CÀI ĐẶT NGĂN XẾP BẰNGDANH SÁCH LIÊN KẾTtemplate <class Node_Entry>struct Node{Node_Entry entry;Node<Node_Entry> *next;Node(); // hàm khởi tạo mặc địnhNode(Node_Entry item, Node<Node_Entry> *link=NULL);};template <class Node_Entry>Node<Node_Entry>::Node(){next = NULL;}template <class Node_Entry>Node<Node_Entry>::Node(Node_Entry item, Node<Node_Entry> *link){entry = item;next = link;}

entrynext

item entry

CÀI ĐẶT NGĂN XẾP BẰNGDANH SÁCH LIÊN KẾTtemplate <class Node_Entry>class Stack {private:

Node<Node_Entry> *top_node;public:

Stack(); // hàm khởi tạo mặc địnhbool empty() const;//bool full() const;bool push(const Node_Entry &item);bool pop();

};

entry

CÀI ĐẶT NGĂN XẾP BẰNGDANH SÁCH LIÊN KẾTtemplate <class Node_Entry>Stack<Node_Entry>::Stack(){

top_node = NULL;}

template <class Node_Entry>bool Stack<Node_Entry>::empty() const{

return (top_node == NULL);}

entry

CÀI ĐẶT NGĂN XẾP BẰNGDANH SÁCH LIÊN KẾTtemplate <class Node_Entry>bool Stack<Node_Entry>::push(const Node_Entry &item){

Node<Node_Entry> *new_top = new Node<Node_Entry>(item, top_node);if (new_top == NULL)

return false;top_node = new_top;return true;

}

entry entry entryitem

CÀI ĐẶT NGĂN XẾP BẰNGDANH SÁCH LIÊN KẾTtemplate <class Node_Entry>bool Stack<Node_Entry>::pop(){Node<Node_Entry> *old_top = top_node;if (empty())return false;top_node = old_top->next; // new top_nodedelete old_top;return true;}

entry entry entryentry

CÀI ĐẶT HÀNG ĐỢI BẰNG DANH SÁCH ĐẶC Mảng tuyến tính (linear array) Mảng vòng (circular array) Hàng đợi trong thực tế?

0 1 2 3

front

4 5 6

rear

0 1 2 3

front

4 5 6 7 8 9

rear

7 8 9

rear

rear

0

CÀI ĐẶT HÀNG ĐỢI BẰNG DANH SÁCH ĐẶC Hàng đợi rỗng Hàng đợi đầy

frontrear front

frontrear rear

CÀI ĐẶT HÀNG ĐỢI BẰNG DANH SÁCH ĐẶCconst max_queue = 100;template <class Entry_Element>class Queue{private:int count; // số phần tửint front; // vị trí đầu hàng đợiint rear; // vị trị cuối hàng đợiEntry_Element entry[max_queue]; public:Queue(); // hàm khởi tạo mặc địnhbool empty() const;bool full() const;bool serve(); // dequeuebool append(const Queue_Entry &item); // enqueue};

item item item item

count = 4

frontrear

CÀI ĐẶT HÀNG ĐỢI BẰNG DANH SÁCH ĐẶCtemplate <class Queue_Element>Queue<Queue_Element>::Queue(){count = 0;front = 0;rear = max_queue - 1;}

front rear

CÀI ĐẶT HÀNG ĐỢI BẰNG DANH SÁCH ĐẶCtemplate <class Queue_Element>bool Queue<Queue_Element>::empty() const{return (count == 0);}

template <class Queue_Element>bool Queue<Queue_Element>::full() const{return (count == max_queue);}

front rear

CÀI ĐẶT HÀNG ĐỢI BẰNG DANH SÁCH ĐẶCtemplate <class Queue_Element>bool Queue<Queue_Element>::append(const Queue_Element &item) {if (full()) // queue đầyreturn false;count++;//rear = ((rear + 1) == max_queue) ? 0 : (rear + 1);rear = (rear + 1) % max_queue;entry[rear] = item;return true;}

front rear

item

rear

item

rear rear

CÀI ĐẶT HÀNG ĐỢI BẰNG DANH SÁCH ĐẶCtemplate <class Queue_Element>bool Queue<Queue_Element>::serve(){if (empty())return false;count--;//front = ((front + 1) == max_queue) ? 0 : (front + 1);front = (front + 1) % max_queue;return true;}

front rearfront front

CÀI ĐẶT HÀNG ĐỢI BẰNG DANH SÁCH LIÊN KẾTtemplate <class Node_Entry>class Queue{private:Node<Node_Entry> *front;Node<Node_Entry> *rear;public:Queue(); // hàm khởi tạo mặc địnhbool empty() const;//bool full() const;bool append(const Node_Entry &item);bool serve();};

Node_Entry

front rear

CÀI ĐẶT HÀNG ĐỢI BẰNG DANH SÁCH LIÊN KẾTtemplate <class Node_Entry>Queue<Node_Entry>::Queue(){front = NULL;rear = NULL;}

template <class Node_Entry>bool Queue<Node_Entry>::empty(){return (front == NULL);}

CÀI ĐẶT HÀNG ĐỢI BẰNG DANH SÁCH LIÊN KẾTtemplate <class Node_Entry>bool Queue<Node_Entry>::append(const Node_Entry &item){Node<Node_Entry> *new_rear = new Node<Node_Entry>(item);if (new_rear == NULL)return false;if (rear == NULL){front = new_rear;rear = new_rear;}else{rear->next = new_rear;rear = new_rear;}

}

Node_Entry

front rear

item

item

CÀI ĐẶT HÀNG ĐỢI BẰNG DANH SÁCH LIÊN KẾTtemplate <class Node_Entry>bool Queue<Node_Entry>::serve(){if (empty())return false;Node<Node_Entry> *old_front = front;front = old_front->next;if (front == NULL) // danh sách có 1 phần tửrear = NULL;delete old_front;return true;

}

Node_Entry

Node_Entry

LỖI THƯỜNG GẶP ‘Không thể lấy nước từ bình rỗng’ Con trỏ đến đối tượng đã bị hủy Chưa qua cầu đã rút ván

p NULL

del

top

top

CƠ CHẾ AN TOÀN

Tại sao cấu trúc liên kết không an toàn? Bộ nhớ không tự hủy Truyền tham biến

Các cơ chế an toàn Cài đặt hàm hủy tạo destructor Định nghĩa chồng toán tử gán Cung cấp hàm khởi tạo mặc định

HÀM HỦY TẠO (DESTRUCTOR) Tại sao cần hàm hủy tạo?

for (int i = 0; i < 1000000; i++){

Stack small;small.push(some_data);

}

some_datatop_node

some_data

some_data

some_data

some_data

HÀM HỦY TẠO (DESTRUCTOR)Stack::~Stack(){

while (!empty())pop(); // hủy Node

}

TOÁN TỬ GÁN(ASSIGNMENT OPERATOR)Stack outer_stack;for (int i = 0; i < 1000000; i++){

Stack inner_stack;inner_stack.push(some_data);inner_stack = outer_stack;

}

outer_stack.top_node

some_data

inner_stack.top_node

some_data

some_data

TOÁN TỬ GÁN(ASSIGNMENT OPERATOR)void Stack::operator=(const Stack &original){

Node *new_top;Node *new_copy;Node *original_node = original.top_node;if (original_node == NULL)

new_top = NULL;else{

new_top = new Node(original_node->entry);while (original_node->next != NULL){

original_node = original_node->next;new_copy->next = new Node(original_node->entry);

new_copy = new_copy->next;}

}}

TOÁN TỬ GÁN(ASSIGNMENT OPERATOR)

original_node

new_top

new_copy

original_top

top_nodetop_node

HÀM KHỞI TẠO SAO CHÉP(COPY CONSTRUCTOR) Hàm khởi tạo mặc định Hàm khởi tạo sao chép Tại sao phải dùng hàm khởi tạo sao chép?

void destroy_the_stack(Stack copy){}int main(){

Stack vital_data;destroy_the_stack(vital_data);

}

out_top

in_top

HÀM KHỞI TẠO SAO CHÉP(COPY CONSTRUCTOR)template <class Node_Entry>Stack<Node_Entry>::Stack(const Stack<Node_Entry> &copy){

Node<Node_Entry> *new_copy;Node<Node_Entry> *original_node = original.top_node;if (original_node == NULL)

top_node = NULL;else{

new_copy = new Node<Node_Entry>(original_node->entry);top_node = new_copy;while (original_node = original_node->next != NULL){

original_node = original_node->next;new_copy->next = new Node<Node_Entry>(original->entry);new_copy = new_copy->next;

}}

}

HÀM KHỞI TẠO SAO CHÉP(COPY CONSTRUCTOR)

original_node

top_node

new_copy

original_top

ỨNG DỤNG THỰC TIỄN

T T TT T CPUT

Giả lặp xử lý song song: cơ chế Round Robin

ỨNG DỤNG THỰC TIỄN

BEGIN...CALL A...

RETURNEND

MAIN

MAIN

BEGIN...CALL B...

RETURNEND

SUB A

SUB A

BEGIN....RETURNEND

SUB B

ỨNG DỤNG THỰC TiỄN

TỔNG KẾT Ứng dụng đa dạng Hàng đợi: công việc có kể thứ tự trước

sau Ngăn xếp: công việc có tính chất quay

lui

THAM KHẢO Tìm kiếm chiều rộng Tìm kiếm chiều sâu Gọi chương trình con Cú pháp hậu tố Lỗi cài toán tử gán Danh sách liên kết vòng Danh sách liên kết kép

ỨNG DỤNG THỰC TIỄN

10 3

5

2 7 12

8 5

510

3

2

10 3 2 7 1

2

712

Tìm kiếm theo chiều rộng

ỨNG DỤNG THỰC TIỄN

10 3

5

2 7 12

8 5

5102

7

10 32 7 1

2

312

Tìm kiếm theo chiều rộng

ỨNG DỤNG THỰC TIỄN

2 * 4 - (9 + 5) (= -6)2 * 4 - 9 + 5 (= 4)

2 4 * 9 5 + -

8

2

44

2

8

9

5

5

9

1414

-6

Cú pháp hậu tố Ban Lan

HÀM HỦY TẠO (DESTRUCTOR) Tại sao cần hàm hủy tạo? Xét ví dụ:

for (int i = 0; i < 1000000; i++){

Stack small;small.push(some_data);

}

some_datatop_node

some_data

some_data

some_data

some_data

HÀM KHỞI TẠO SAO CHÉP(COPY CONSTRUCTOR)

top_node

original_top

x x

LIÊN KẾT KÉP, LIÊN KẾT VÒNG

min max

List

top related