Thuật toán đệ quy

6 615 2
Thuật toán đệ quy

Đang tải... (xem toàn văn)

Thông tin tài liệu

1.1 Khái niệm đệ quy Thuật toán đệ qui là một trong những sự mở rộng của khái niệm thuật toán. Như đã biết, một thuật toán được đòi hỏi phải thỏa mãn các tính chất: Tính xác định. Tính hữu hạn hay tính dừng. Tính đúng. Tuy nhiên có những trường hợp việc tìm ra một thuật toán với những tính chất đòi hỏi như trên rất khó khăn nhưng có cách giải có thể vi phạm các tính chất của thuật toán nhưng lại khá đơn giản và được chấp nhận. Ví dụ những trường hợp bài toán có thể được phân tích và đưa tới việc giải một bài toán cùng loại nhưng cấp độ thấp hơn, chẳng hạn cở dữ liệu nhập nhỏ hơn, giá trị cần tính toán nhỏ hơn, v.v Ta cũng thường thấy những định nghĩa về những đối tượng, những khái niệm dựa trên chính những đối tượng, những khái niệm đó như những ví dụ dưới đây. Ví dụ 1: Ðịnh nghĩa giai thừa. Giai thừa của một số tự nhiên n, ký hiệu là n!, được định nghĩa bằng cách qui nạp như sau: 0! = 1, n! = (n-1)!*n, với mọi n > 0. Ví dụ 2: Ðịnh nghĩa dãy số Fibonacci { f 1 , f 2 , . . ., f n , } : f 0 = 1, f 1 = 1, f n = f n-1 + f n-2 , vớ mọi n > 1. Thuật toán để giải các bài toán trong những trường hợp như trên thường được viết dựa trên chính nó, tức là trong các bước của thuật toán có thể có trường hợp thực hiện lại chính thuật toán đó (nhưng thường là với dữ liệu nhập có cở thấp hơn, hay có cấp độ thấp hơn). Những thuật toán loại nầy được gọi là những thuật toán đệ quy. Dưới đây là các thuật toán đệ quy tính giai thừa của một số tự nhiên n và tính số hạng thứ n của dãy số Fibonacci. Thuật toán đệ quy tính giai thừa của một số tự nhiên. Input : số tự nhiên n. Output : F (n) bằng n!. Thuật toán : 1. F := 1 2. if n > 0 then F := F(n-1) * n; { Tính (n-1)! rồi nhân với n sẽ được giá trị F} 3. Output F. Thuật toán đệ quy tính số hạng thứ n của dãy số Fibonacci. Input : số nguyên dương n. Output : F (n) bằng số hạng thứ n của dãy Fibonacci. Thuật toán : 1. if n=0 or n=1 then F := 1; 2. if n > 1 then F := F(n-1) + F(n-2) { tức là tính F(n-1) và F(n-2) rồi tính tổng số của các giá trị nầy để gán cho F} 3. Output F. Trong thuật toán tính giai thừa n ở trên, có một bước mà ta tính (n-1)! để từ đó tính ra kết quả. Ðó là bước 2 trong trường hợp n > 0. Chính bước tính (n-1)! nầy trong thuật toán làm cho thuật toán trở thành thuật toán đệ quy. Ta còn gọi bước nầy là bước thực hiện đệ quy. Trong thuật toán tính số hạng thứ n, ký hiệu F(n), của dãy số Fibonacci ở trên ta phải tính F(n-1) và F(n-2) nếu n > 1 trong bước 2. Bước tính F(n- 1) và F(n-2) nầy chính là bước đệ quy của thuật toán. Thuật toán đệ quy đã vi phạm tính xác định và rõ ràng của thuật toán vì ở các bước đệ quy của nó. Tuy nhiên ta vẫn chấp nhận các thuật toán đệ quy vì nó tiện lợi trong nhiều trường hợp chẳng hạn như việc cài đặt các định nghĩa đệ quy hay trong những trường hợp bài toán có thể được đưa về bài toán cùng loại ở mức độ thấp hơn. Hơn nữa các ngôn ngữ lập trình đều cho phép ta viết các chương trình con (thủ tục hay hàm) dưới dạng đệ quy. Ưu thế của thuật toán đệ quy là khi suy nghĩ về phương pháp giải bài toán bằng cách phân chia trường hợp mà trong đó có những trường hợp bài toán được thu gọn về bài toán cùng loại với cấp độ thấp hơn, và những trường hợp nầy chính là những trường hợp mà ta phải thực hiện bước đệ quy. Còn những trường hợp khác thì ta có thể giải quyết trực tiếp một cách dễ dàng, và ta gọi những trường hợp nầy là những trường hợp dừng đệ quy. Ví dụ như trong việc tính số hạng F(n) ứng với chỉ số n của dãy Fibonacci thì trường hợp n = 0 và trường hợp n = 1 là các trường hợp dừng đệ quy, còn trường hợp n > 1 là trường hợp mà ta phải thực hiện các bước đệ quy: tính các số hạng F(n-1) và F(n-2) để suy ra số hạng F(n). 1.2 Cấu trúc của thuật toán đệ quy Trong thuật giải đệ qui thường gồm 2 phần: phần cơ sở và phần đệ quy. Phần cơ sở gồm các trường hợp không cần thực hiện lại thuật toán, tức là các trường hợp dừng mà ta có thể trực tiếp giải quyết được bài toán (hay không có yêu cầu gọi đệ qui). Trong thuật toán tìm số hạng thứ n của dãy Fibonacci ở trên, bước 1 trong thuật toán là phần cơ sở của thuật giải đệ qui. Phần đệ quy là phần trong thuật toán có yêu cầu gọi đệ quy, tức là yêu cầu thực hiện lại thuật toán ở cấp độ thấp hơn. Trong thuật toán tìm số hạng thứ n của dãy Fibonacci ở trên, bước 2 trong thuật toán là phần đệ quy. Trong phần đệ quy, yêu cầu gọi đệ qui thường được đặt trong một điều kiện kiểm tra việc gọi đệ quy. Cần lưu ý rằng phần cơ sở luôn luôn phải có hay nói cách khác là phần đệ quy luôn luôn phải nằm trong điều kiện kiểm soát dừng đệ quy, vì nếu không thì thuật toán sẽ bị lặp vô hạn do việc gọi đệ quy luôn được thực hiện. Về mặt cài đặt, nếu như có sử dụng biến cục bộ trong thủ tục hay hàm đệ quy thì các biến nầy được tạo ra và được đặt trong vùng nhớ "STACK". Do đó quá trình gọi đệ quy dễ gây ra tình trạng tràn stack (stack overflow). Trong nhiều trường hợp có thể được người ta tìm cách viết lại thuật toán đệ quy dưới dạng lặp. Thuật toán đệ qui để tìm số hạng thứ n của dãy số Fibonacci và thuật toán tính n! có thể được viết lại dưới dạng lặp như sau: Thuật toán lặp tính số hạng thứ n của dãy số Fibonacci. Input : số nguyên dương n. Output : F (n) bằng số hạng thứ n của dãy Fibonacci. Thuật toán : 1. a := 1 2. F := 1 3. for i:=3 to n do begin temp := a + F; a := F; F := temp; end; 4. Output F. Thuật toán lặp tính giai thừa của một số tự nhiên. Input : số tự nhiên n. Output : F (n) bằng n!. Thuật toán : 1. F := 1 2. for i := 2 to n do F := F * i 3. Output F. 1.3 Trình bày (hay viết) thuật toán đệ quy Ðể tiện trình bày thuật toán đệ quy, nhất là ở các bước gọi đệ quy (hay thực hiện đệ quy), ta thường đặt tên cho thuật toán có đi kèm các tham biến chính liên quan đến bài toán cũng giống như ta khai báo thủ tục hay hàm trong các chương trình máy tính. Dưới đây ta xét 2 ví dụ khác về các bài toán mà ta có thể giải bằng phương pháp đệ quy. Ví dụ 1: Tính tổ hợp n chọn k, ký hiệu là C(n,k). Nhắc lại một số tính chất của C(n,k): C(n,0) = C(n,n) = 1, và C(n,k) = C(n-1,k) + C(n-1,k-1) nếu 0 < k < n. Các tính chất trên của phép tính tổ hợp cho ta một cách tính tổ hợp theo phương pháp đệ quy. Ðặt tên cho thuật toán tính tổ hợp n chọn k là Tohop(n,k) ta có thuật toán đệ quy để tính tổ hợp sau đây: Thuật toán tính tổ hợp n chọn k: Tohop(n,k) If (k = 0) or (k = n) then Tohop := 1; If (0 < k) and (k < n) then Tohop := Tohop(n-1, k) + Tohop(n-1, k-1); Ví dụ 2: Tính ước số chung lớn nhất của 2 số tự nhiên a và b, ký hiệu là USCLN(a,b). Từ các tính chất dưới đây (cho các số nguyên tùy ý) của phép tính ước số chung lớn nhất: USCLN(a, 0) = USCLN(0, a) = a, USCLN(a, b) = USCLN(a-b, b), và USCLN(a, b) = USCLN(a, b-a) Ta có ngay một cách tính USCLN theo phương pháp đệ quy. Ðặt tên cho thuật toán tính USCLN của 2 số tự nhiên a và b là USCLN(a, b) ta có thuật toán đệ quy sau đây: Thuật toán tính USCLN của a và b: USCLN(a,b) If (a = 0) or (b = 0) then USCLN := a+b; Else If (a > b) then USCLN := USCLN(a-b, b); Else USCLN := USCLN(a, b -a); Ghi chú: Một ví dụ khá tốt để minh họa cho thuật toán đệ quy cũng thường được đề cập tới là bài toán "Tháp Hà Nội". Chúng ta có thể tham khảo về bài toán nầy trong [5] trang 227. . chính là bước đệ quy của thuật toán. Thuật toán đệ quy đã vi phạm tính xác định và rõ ràng của thuật toán vì ở các bước đệ quy của nó. Tuy nhiên ta vẫn chấp nhận các thuật toán đệ quy vì nó tiện. Những thuật toán loại nầy được gọi là những thuật toán đệ quy. Dưới đây là các thuật toán đệ quy tính giai thừa của một số tự nhiên n và tính số hạng thứ n của dãy số Fibonacci. Thuật toán đệ quy. bằng n!. Thuật toán : 1. F := 1 2. for i := 2 to n do F := F * i 3. Output F. 1.3 Trình bày (hay viết) thuật toán đệ quy Ðể tiện trình bày thuật toán đệ quy, nhất là ở các bước gọi đệ quy (hay

Ngày đăng: 29/10/2014, 20:00

Từ khóa liên quan

Tài liệu cùng người dùng

Tài liệu liên quan