CÁC THUẬT TOÁN
TRÊN ĐỒ THỊ
MỤC TIÊU
Một số khái niệm cơ bản
Biểu diễn đồ thị
Duyệt đồ thị
Thành phần liên thông và thành phần liên thông mạnh
Đồ thị định hướng không có chu trình
Sắp xếp topo
Các thuật toán đồ thị
Đường đi ngắn nhất
Cây bao trùm ngắn nhất
MỘT SỐ KHÁI NIỆM CƠ BẢN
Đồ thị được sử dụng để mô hình hóa các bài
toán bao gồm một tập các đối tượng có quan
hệ với nhau theo 1 cách nào đó
Ví dụ
Một mạng truyền thông
Bản đồ đường đi giữa các thành phố
Việc giải quyết các bài toán trở thành việc giải
quyết một bài toán trên đồ thị
Chẳng hạn
Tìm đường đi ngắn nhất
Tìm cây bao trùm ngắn nhất
Tìm các thành phần liên thông…
MỘT SỐ KHÁI NIỆM CƠ BẢN
Một đồ thị định hướng G = <V, E>
V là tập các đỉnh, E là tập các cung nối các đỉnh
Mỗi cung là một cặp đỉnh có thứ tự (u,v), ký hiệu u->v
Nếu có cung (u,v) ta nói đỉnh v kề với đỉnh u
u v
a b
c d
Một cung của đồ thị
Đồ thị định hướng
MỘT SỐ KHÁI NIỆM CƠ BẢN
Một đồ thị vô hướng G = <V, E>
V là tập các đỉnh, E là tập các cạnh nối các đỉnh
Mỗi cạnh là một cặp đỉnh không có thứ tự (u,v)
Nếu có cạnh (u,v) ta nói đỉnh u và v kề nhau
u v
a b
c d
e
Một cạnh của đồ thị
Đồ thị vô hướng
MỘT SỐ KHÁI NIỆM CƠ BẢN
Đồ thị có trọng số
Đồ thị mà mỗi cung/cạnh của đồ thị được gắn với một số
c(u,v)
Số c(u,v) được gọi là trọng số (giá/độ dài) của cung/cạnh
(u,v)
Đường đi đơn
Là một dãy hữu hạn các đỉnh (v
0
, v
1
, …, v
k
) khác nhau, ngoại
trừ có thể v
0
= v
k
, và v
i+1
là đỉnh kề của v
i
(i=1,2…k-1)
Với đồ thị có trọng số độ dài đường đi được tính là tổng
trọng số trên các cạnh trên đường đi
Với đồ thị không có trọng số độ dài đường đi là k
MỘT SỐ KHÁI NIỆM CƠ BẢN
Đồ thị đơn
Là đồ thị vô hướng có nhiều nhất một cạnh nối hai đỉnh
Là đồ thị vô hướng mà hai đỉnh có thể được nối bởi nhiều
hơn một cạnh
Đa đồ thị
MỘT SỐ KHÁI NIỆM CƠ BẢN
Chu trình
Là đường đi khép kín, tức là đường đi (v
0
, v
1
, …, v
k
) có v
0
= v
k
Ví dụ
Trong đồ thị định hướng dưới đây thì (v
4
, v
1
, v
2
, v
3
) là một
đường đi từ v
4
đến v
3
, và (v
4
, v
1
, v
2
, v
4
) là một chu trình
v
1
v
2
v
4
v
3
MỘT SỐ KHÁI NIỆM CƠ BẢN
Đồ thị con
Đồ thị G’=<V’, E’> là đồ thị con của G=<V, E> nếu V’ V và
E’ E
Ví dụ
v
1
v
2
v
4
v
3
v
1
v
2
v
4
Đồ thị con
Đồ thị
BIỂU DIỄN ĐỒ THỊ
Để giải quyết các vấn đề của đồ thị, cần lưu trữ đồ
thị trong bộ nhớ máy tính, vì thế cần phải biểu
diễn CTDL của đồ thị.
Có hai cách biểu diễn
Biểu diễn bằng ma trận kề (lưu trữ đồ thị bằng mảng hai
chiều)
Biểu diễn bằng danh sách kề (lưu trữ đồ thị bằng danh
sách móc nối)
BIỂU DIỄN ĐỒ THỊ BẰNG MA TRẬN KỀ
Với đồ thị không có trọng số G=<V,E>, với V={v
1
, v
2
, …, v
n
},
được lưu trữ trong mảng hai chiều A[1 n][1 n] trong đó:
A[i,j] =
Ví dụ: cho đồ thị vô hướng
1 Nếu (v
i
, v
j
) có cạnh nối
0 Nếu (vi, vj) không có cạnh nối
1 2
3 4
5
Đồ thị vô hướng
0 1 1 1 0
1 0 0 1 1
1 0 0 1 0
1 1 1 0 1
0 1 0 1 0
Mảng biểu diễn đồ thị
BIỂU DIỄN ĐỒ THỊ BẰNG MA TRẬN KỀ
Với đồ thị không có trọng số G=<V,E>, với V={v
1
, v
2
, …, v
n
},
được lưu trữ trong mảng hai chiều A[1 n][1 n] trong đó:
A[i,j] =
Ví dụ 1: cho đồ thị vô hướng
1 Nếu (v
i
, v
j
) có cung/cạnh nối
0 Nếu (vi, vj) không có cung/cạnh nối
1 2
3 4
5
Đồ thị vô hướng
0 1 1 1 0
1 0 0 1 1
1 0 0 1 0
1 1 1 0 1
0 1 0 1 0
Mảng biểu diễn đồ thị
BIỂU DIỄN ĐỒ THỊ BẰNG MA TRẬN KỀ
Ví dụ 2: cho đồ thị định hướng
Nhận xét:
Ưu điểm: Với 2 đỉnh bất kỳ ta biết ngay rằng có cung/cạnh nối
hay không trọng số của cung/cạnh đó (nếu là đồ thị trọng số)
Nhược điểm: Lãng phí bộ nhớ (do chỉ có một số cung/cạnh)
1 2
3 4
5
Đồ thị định hướng
0 1 0 1 0
0 0 0 1 1
1 0 0 0 0
0 0 1 0 0
0 0 0 1 0
Mảng biểu diễn đồ thị
BIỂU DIỄN ĐỒ THỊ BẰNG MA TRẬN KỀ
Với đồ thị có trọng số G=<V,E>, với V={v
1
, v
2
, …, v
n
}, với
c(v
i
, v
j
) là trọng số trên cung/cạnh (v
i
, v
j
), khi đó:
A[i,j] =
Ví dụ 1: cho đồ thị định hướng
c (vi, vj) Nếu (v
i
, v
j
) có cung/cạnh nối
0 Nếu (vi, vj) không có cung/cạnh nối
0 12 0 10 0
0 0 0 5 25
9 0 0 0 0
0 0 6 0 0
0 0 0 27 0
Mảng biểu diễn đồ thị
1 2
3 4
5
Đồ thị định hướng
12
10
25
27
6
9
5
BIỂU DIỄN ĐỒ THỊ BẰNG DANH SÁCH KỀ
Cách biểu diễn
Với mỗi đỉnh, lập một danh sách các đỉnh kề với nó
Danh sách các đỉnh kề là một danh sách móc nối
Mỗi thành phần trong danh sách gồm số hiệu đỉnh, trọng số
của cung/cạnh nối
Sử dụng mảng A[1 n], trong đó A[i] là con trỏ trỏ tới đầu
danh sách các đỉnh kề của đỉnh thứ I
Nhận xét:
Ưu điểm: Tiết kiệm bộ nhớ
Nhược điểm: muốn biết có cung/cạnh (v
i
, v
j
) hay không (và
trọng số của nó) ta phải duyệt danh sách các đỉnh kề của v
i
.
BIỂU DIỄN ĐỒ THỊ BẰNG DANH SÁCH KỀ
Ví dụ :
cho đồ thị định hướng
1 2
3 4
5
Đồ thị định hướng
12
10
25
27
6
9
5
2 12
4 5
1 9
2
1
3
4
5
4 10
5 25
3 6
4 27
Mảng các danh sách kề
Mảng A
BIỂU DIỄN ĐỒ THỊ BẰNG DANH SÁCH KỀ
Cấu trúc dữ liệu
#define N 100
struct node
{
unsigned int index; //số hiệu đỉnh
float cost; //trọng số cung/cạnh
struct node *next;
};
typedef struct member *node;
member A[N];
TÌM KIẾM TRÊN ĐỒ THỊ
Có hai phương pháp
Tìm kiếm theo chiều rộng – Breath First Search
Tìm kiếm theo chiều sâu – Depth First Search
TÌM KIẾM THEO CHIỀU RỘNG
Chọn một đỉnh u và thăm đỉnh đó
Từ đỉnh u lần lượt thăm các đỉnh v kề u và chưa
được thăm.
Đỉnh v nào được thăm trước thì các đỉnh kề nó cũng
được thăm trước
Quá trình trên được tiếp tục cho tới khi không thể
đến thăm đỉnh nào nữa.
TÌM KIẾM THEO CHIỀU RỘNG
Ví dụ: cho đồ thị
1 2
3 4
5
6 7
9 8
Xuất phát từ đỉnh 1
1
2
3
4
5
6
7
9
8
Quá trình đi thăm từ
đỉnh u sẽ tạo ra cây
gốc u
TÌM KIẾM THEO CHIỀU RỘNG
Thuật toán
Cho G=<V, E> với V={1, 2, n}
Sử dụng hàng đợi Q để lưu các đỉnh đã được thăm
nhưng chưa thăm các đỉnh kề của nó
Sử dụng mảng father[1 n] để lưu lại vết của đường đi
xuất phát từ đỉnh u, father[w] = v nếu w được thăm từ v.
Ban đầu mảng father được khởi tạo giá trị -1
Danh sách các đỉnh kề của v ký hiệu là Adj(v)
TÌM KIẾM THEO CHIỀU RỘNG
Procedure BFS(u)
{
Father[u]=0;
Creat(Q);
Add(Q,u);
While not empty(Q) Do
{ Del(Q,v);
For mỗi w trong Adj(v) Do
if father[w]= -1 then
{ father[w]=v;
Add(Q,w);
}
}
}
TÌM KIẾM THEO CHIỀU RỘNG
Procedure BreathTravelsal(G)
{
for u=1 to n do father[u]=-1;
for u=1 to n do
if father[u]=-1 then BFS(u);
}
Chú ý: nếu G là đồ thị không có trọng số thì khi gọi thủ tục
BFS(u) tìm ra đường đi ngắn nhất từ u đến các đỉnh có
thể đạt tới từ u, sử dụng mảng father để xây dựng đường
đi ngắn nhất tìm ra.
TÌM KIẾM THEO CHIỀU SÂU
Xuất phát từ đỉnh u được thăm
Thăm đỉnh w là đỉnh kề của u chưa được thăm
Tìm kiếm theo chiều sâu xuất phát từ w
Khi một đỉnh v đã được thăm mà mọi lân cận của nó đã được
thăm, phép tìm kiếm quay lại đỉnh cuối cùng vừa được thăm
mà đỉnh kề w của nó chưa được thăm, một phép tìm kiếm
theo chiều sâu xuất phát từ w được thực hiện.
TÌM KIẾM THEO CHIỀU SÂU
Ví dụ: cho đồ thị
1 2
3 4
5
6 7
9 8
Xuất phát từ đỉnh 1
Thứ tự các đỉnh được thăm:
1, 2, 4, 3 (quay lại 2), 5, 6, 7, 8, 9