Trong bài viết này, chúng ta sẽ tìm hiểu về vòng lặp – loop. Vòng lặp là một trong những khái niệm quan trọng trong MAXScript. Kết hợp với function đã học ở bài 4, vòng lặp giúp script của bạn thực thi số tác vụ mà không sức người nào địch lại được.
Nó cũng là thứ đầu tiên giúp script của bạn trở nên bắt đầu có giá trị lớn về năng suất, khi có thể giải quyết những công việc lặp đi lặp lại chỉ trong một lần chạy lệnh. Dưới đây, tôi sẽ giới thiệu những cách sử dụng cơ bản nhất của các vòng lặp. Các bài viết sau, chúng ta sẽ đi sâu hơn vào từng vòng lặp cụ thể để ứng dụng vào trong công việc.
MỤC LỤC
Các kiểu vòng lặp
Trong MAXScript, chúng ta có 3 kiểu vòng lặp chính. Đó chính là vòng lặp For, vòng lặp While, và vòng lặp kết hợp 2 loại trước. Ở bài viết này, tôi tạm gọi kiểu vòng lặp cuối là vòng lặp kết hợp. Điểm khác biệt chính giữa 3 kiểu này là ở điều kiện của vòng lặp:
- vòng lặp For thường sẽ lặp lại một số lần nhất định.
- vòng lặp While thường sẽ lặp lại một số lần không nhất định.
- vòng lặp kết hợp sẽ lặp lại một số lần không nhất định, nhưng có giới hạn tối đa.
Trên thực tế, không có quy định cụ thể về cách sử dụng cụ thể vòng lặp cho các trường hợp khác nhau. Rất nhiều tình huống bạn có thể sử dụng vòng lặp For thay cho While và ngược lại. Tuy nhiên, nên xác định đúng kiểu vòng lặp để tối ưu code, tránh trường hợp xấu nhất là vòng lặp không thể kết thúc, hoặc gây crash 3ds Max.
Với người mới, vòng lặp For sẽ dễ hiểu và hay được ưu tiên sử dụng hơn, sau đó sẽ là vòng lặp While, và cuối cùng là kiểu vòng lặp kết hợp. Phía dưới là một ví dụ để giúp bạn dễ hình dung cách xác định cụ thể kiểu vòng lặp script của mình:
- với tác vụ “đếm từ 1 đến 100”, chúng ta sẽ sử dụng vòng lặp For.
- với tác vụ “đếm từ 1 đến khi khản giọng”, chúng ta sẽ sử dụng While.
- với tác vụ “đếm từ 1 đến 100 nếu không bị khản giọng”, chúng ta sẽ sử dụng vòng lặp kết hợp.
Vòng lặp For
Khác với vòng lặp While, vòng lặp For có khá nhiều tùy chọn. Trong phần này, do chúng ta chưa làm quen với các khái niệm nâng cao như mảng (array), tôi sẽ tạm thời chỉ trình bày một vài ví dụ đơn giản của vòng lặp For. Cấu trúc mà chúng ta sẽ học trong hôm nay là:
for i = x (giá trị đầu) to y (giá trị cuối) by z (bước nhảy) do <câu lệnh>
Trong cấu trúc trên, i là biến chúng ta khai báo để kiểm soát vòng lặp. Bạn có thể thay i bằng bất kỳ chữ cái hoặc cụm từ nào khác. Giá trị đầu x, giá trị cuối y, và bước nhảy z có thể là số nguyên (integer), số thực (float) hoặc thời gian (time). Khi mới học, chúng ta hầu như sẽ sử dụng kiểu số nguyên (integer) cho vòng lặp. Bước nhảy z có giá trị mặc định là 1 và không bắt buộc phải khai báo.
Hãy mở 3ds Max và setup để sẵn sàng soạn thảo script. Nhập vào cửa sổ MAXScript Editor dòng lệnh sau. Như mọi lần, hãy nhập nó bằng tay để làm quen với việc soạn thảo lệnh:
for i = 1 to 5 do messageBox "OK"
Thử evaluate câu lệnh phía trên. Bạn sẽ thấy cửa sổ thông báo “OK” của 3ds Max hiện ra đúng 5 lần. Trong câu lệnh trên, chúng ta gán biến i giá trị khởi điểm là 1. 3ds Max mặc định hiểu đây là số nguyên. Nếu muốn sử dụng số thực, chúng ta sẽ viết 1.0. Vì chúng ta không khai báo bước nhảy, 3ds Max sẽ dùng bước nhảy mặc định là 1. Ở đây, mỗi lần i tăng 1 đơn vị, câu lệnh messageBox “OK” sẽ được thực hiện một lần. Đến khi i đạt giá trị vượt quá 5, 3ds Max sẽ dừng vòng lặp.
Để quan sát rõ ràng hơn, hãy chỉnh sửa câu lệnh trên như sau:
for i = 1 to 5 do messageBox ("Vong lap so: " + i as string)
Bạn sẽ thấy lần này, 3ds Max hiển thị hộp thoại 5 lần, lần lượt thông báo là: “Vong lap so: 1”, “Vong lap so: 2”, “Vong lap so: 3”, “Vong lap so: 4”, “Vong lap so: 5”. Vậy tức là, ta có thể lợi dụng giá trị của biến i, tức số vòng lặp hiện tại để có thể thay đổi kết quả trả về.
Vòng lặp While
Vòng lặp While có cách sử dụng đơn giản hơn so với vòng lặp For. Nó có 2 dạng cấu trúc:
while <điều kiện> do <câu lệnh>
do <câu lệnh> while <điều kiện>
Cả 2 cấu trúc trên gần tương đương nhau. Chúng khác biệt ở chỗ cấu trúc đầu tiên sẽ kiểm tra điều kiện trước khi thực hiện câu lệnh, còn câu lệnh số 2 sẽ thực hiện câu lệnh xong mới kiểm tra điều kiện. Tức là cấu trúc đầu tiên có thể sẽ không thực hiện câu lệnh một lần nào hết. Trong khi đó, cấu trúc số 2 sẽ luôn thực hiện ít nhất 1 lần đầu tiên.
Hãy nhập vào MAXScript Editor câu lệnh sau:
i = 5 while i > 0 do ( messageBox ("Gia tri hien tai: " + i as string) i = i - 1 )
Với câu lệnh i = i -1, giá trị của i sẽ giảm đi 1 sau mỗi vòng lặp. Thực thi câu lệnh trên. Bạn sẽ thấy các thông báo hiện ra lần lượt là “Gia tri hien tai: 5”, “Gia tri hien tai: 4”, “Gia tri hien tai: 3”, “Gia tri hien tai: 2”, “Gia tri hien tai: 1”. Ở lần lặp số 6, giá trị của i = 0, điều kiện i > 0 không còn đúng nữa, vì thế vòng lặp dừng lại, và không có thông báo nào hiện ra.
Vậy nếu không có câu lệnh i = i – 1, hoặc nếu <điều kiện> luôn đúng thì điều gì sẽ xảy ra? Hãy thử câu lệnh dưới. Cảnh báo: đừng chạy câu lệnh này trên file đang làm việc của bạn!
while 3 > 2 do messageBox ""
Vì điều kiện “3 > 2” là luôn luôn đúng nên vòng lặp này sẽ không bao giờ kết thúc. 3ds Max sẽ hiển thị thông báo vô hạn không có điểm dừng. Bạn sẽ phải dùng đến Task Manager để “kill” phần mềm để thoát khỏi script. Thật đáng sợ phải không, chỉ với vài dòng, chúng ta đã có thể viết ra 1 con “virus” phá hoại cỡ nhỏ dành cho 3ds Max.
Chính vì vậy, như đã nói ở trên, việc xác định đúng kiểu vòng lặp rất quan trọng, vì bạn có thể làm crash hoặc treo 3ds Max với vòng lặp vô tận kiểu như trên.
Vòng lặp kết hợp
Bạn có thể tích hợp điều kiện while vào trong vòng lặp for theo cấu trúc sau:
for <số lần lặp> while <điều kiện> do <câu lệnh>
Với cấu trúc này, vòng lặp sẽ lặp đủ số lần lặp nếu <điều kiện> vẫn còn được thỏa mãn. Hãy thử ví dụ sau:
for i = 10 to 0 by -2 while i > 2 do messageBox ("Gia tri hien tai: " + i as string)
Tôi sử dụng bước nhảy là -2, vì thế biến i sẽ có giá trị lần lượt là 10, 8, 6, 4, 2, 0 qua các vòng lặp. Bởi điều kiện i > 2 được thêm vào, nên câu lệnh sẽ kết thúc khi i = 2. Bạn sẽ nhận được các thông báo lần lượt là “Gia tri hien tai: 10”, “Gia tri hien tai: 8”, “Gia tri hien tai: 6”, “Gia tri hien tai: 4”.
Bài tập ứng dụng
Trên đây mới chỉ là cái nhìn tổng quan lý thuyết về vòng lặp. Còn rất nhiều tùy chọn nâng cao khác, đặc biệt với vòng lặp For, mà chúng ta sẽ học ở các bài tiếp theo. Trong phần này, chúng ta sẽ có 3 bài tập lý thuyết đơn giản để thí dụ về vòng lặp:
- Bài tập 1: cho số nguyên x bất kỳ (ví dụ x = 3). Nhân x với 5, sau đó trừ 4, lặp lại 10 lần. Sử dụng vòng lặp For để tính ra kết quả cuối cùng. Dùng lệnh messageBox để in ra đáp án.
- Bài tập 2: cho số nguyên x bất kỳ (ví dụ x = 7). Sử dụng vòng lặp While để tìm bội lớn nhất của x mà nhỏ hơn 999. Dùng lệnh messageBox để thông báo đáp án.
- Bài tập 3: cho số nguyên x bất kỳ (ví dụ x = 6). Sử dụng vòng lặp kết hợp để tìm tất cả các bội của x mà nhỏ hơn 333. Dùng lệnh print để in ra đáp án.
Lời giải bài tập
Lưu ý: hãy cố gắng giải bài tập trước khi xem lời giải. Dùng chuột bôi đen đoạn dưới để thấy đáp án. Nếu có thể, hãy thử nghĩ ra một cách giải khác.
Bài tập 1:
x = 3
for i = 1 to 10 do x = (x * 5) - 4
messageBox (x as string)
Bài tập 2:
x = 7
while (x + 7) < 999 do x = x + 7
messageBox (x as string)
Bài tập 3:
x = 0 for i = 1 to 1000 while (x + 6) < 333 do ( x = x + 6 print x )