Tệp tin
Đã giới thiệu| English | Ý nghĩa |
|---|---|
| file/faɪl/ | tệp tin |
| text file/tekst faɪl/ | tệp văn bản |
| secondary storage/ˈsekəndəri ˈstɔːrɪdʒ/ | b bộ lưu trữ phụ |
| persistence/pəˈsɪstəns/ | tính bền vững |
| end of file/end ɒv faɪl/ | cuối tệp |
| separator/ˈsepəreɪtə/ | kí tự phân cách |
| sequential/siːˈkwenʃl/ | thứ tự tuần tự |
Trò chơi đã ghi nhớ
- Cho đến năm 1987, việc tắt máy chơi game sẽ xóa sạch mọi thứ. Mỗi phiên chơi đều bắt đầu từ màn hình đầu tiên; một trò chơi dài là một buổi chiều dài hoặc vô nghĩa.
- The Legend of Zelda được cung cấp kèm một viên pin nhỏ bên trong băng mang giúp giữ sống vài trăm byte dữ liệu. Lần đầu tiên một trò chơi gia đình có thể lưu và tiếp tục từ nơi bạn đã dừng lại.
- Mọi điểm cao, mọi tài liệu, mọi cài đặt nào bạn từng giữ lại đều tồn tại vì lý do tương tự: RAM quên khi mất điện, nhưng một tệp tin thì không.
- Bài học này giải thích tại sao tệp tin tồn tại và cách giả mã đọc và ghi một tệp văn bản, dòng theo dòng.
Tại sao cần tệp tin
- Biến sống trong RAM và biến mất khi chương trình kết thúc. Một tệp tin trên bộ nhớ phụ giữ dữ liệu giữa các lần chạy chương trình: tính bền vững.
- Tệp tin cho phép đầu ra của một chương trình trở thành đầu vào của chương trình khác, giúp dữ liệu có thể được chia sẻ.
- Một tệp tin có thể chứa nhiều hơn dung lượng bộ nhớ, và một chương trình có thể khởi động lại từ trạng thái đã lưu.

Biến biến mất ở cuối lần chạy; tệp tin vẫn còn đó ngày mai
Tại sao một chương trình nên viết dữ liệu vào tệp tin thay vì giữ nó trong biến?
Difficulty 1/5 · 100 coins + a small bonus on first completion today
RAM là bộ nhớ tạm, nên dữ liệu bị mất khi thoát. Tệp tin trên bộ nhớ phụ tồn tại giữa các lần chạy.
Tệp văn bản và ba chế độ
- Một tệp văn bản lưu dữ liệu dưới dạng các dòng ký tự, mà chương trình đọc và ghi từng dòng một, bắt đầu từ đầu. Chuỗi các dòng này chính là điều làm cho vòng lặp có thể duyệt qua nó.
OPENFILE … FOR READđọc từ dòng đầu tiên.FOR WRITEtạo một tệp mới, hoặc ghi đè lên tệp hiện có.FOR APPENDthêm các dòng mới vào cuối, giữ nguyên những gì đang có.- Mở trước khi dùng, đóng sau khi dùng. Một tệp chỉ có một chế độ tại một thời điểm.
Khớp mỗi chế độ mở tệp với chức năng của nó.
Difficulty 2/5 · 140 coins + a small bonus on first completion today
ĐỌC đọc; VIẾT ghi đè từ đầu; KÉO DÀI thêm vào cuối mà không mất những gì đang có.
Để thêm dòng vào cuối một tệp tin hiện có mà không mất nội dung, hãy mở nó theo chế độ ____.
Difficulty 1/5 · 100 coins + a small bonus on first completion today
VIẾT sẽ tạo tệp rỗng. KÉO DÀI giữ những gì đang có và viết sau đó.
Đọc mọi dòng
OPENFILE "data.txt" FOR READ
WHILE NOT EOF("data.txt") DO
READFILE "data.txt", LineString
OUTPUT LineString
ENDWHILE
CLOSEFILE "data.txt"
EOFkiểm tra cuối tệp. Kiểm tra nó trước mỗi lần đọc: đọc vượt quá cuối tệp là lỗi.CLOSEFILEquan trọng: dữ liệu đệm có thể bị mất và các chương trình khác bị khóa ra khỏi tệp đang mở.
Xử lý tệp tin: mở → sử dụng → đóng
Trải qua chu kỳ sống mà mọi tệp tin đều tuân theo. Hai phần dễ bị quên nhất là kiểm tra EOF khi đọc trong vòng lặp, và luôn đóng ở cuối.
EOF kiểm tra điều gì?
Difficulty 1/5 · 100 coins + a small bonus on first completion today
EOF (cuối tệp) được kiểm tra trước mỗi lần đọc để vòng lặp dừng lại khi không còn dữ liệu nữa.
Tại sao bạn phải luôn đóng tệp sau khi sử dụng nó?
Difficulty 1/5 · 100 coins + a small bonus on first completion today
Đóng đẩy các phép viết đã đệm vào đĩa và giải phóng khóa để các chương trình khác có thể sử dụng tệp.
Ghi các dòng
OPENFILE "log.txt" FOR WRITE
FOR i ← 1 TO 100
WRITEFILE "log.txt", "Event " & NUM_TO_STR(i)
NEXT i
CLOSEFILE "log.txt"
WRITEkhởi tạo tệp rỗng. Để thêm vào nhật ký phải giữ lịch sử, hãy mở nóFOR APPENDthay thế.- Một tệp văn bản chứa chuỗi: một số được chuyển đổi với
NUM_TO_STRkhi xuất ra.
Ví dụ minh họa: ba dòng cuối của một tệp
- Viết thủ tục
LastLines(FileName)xuất ra ba dòng cuối của một tệp văn bản, theo thứ tự.
PROCEDURE LastLines(BYVAL FileName : STRING)
DECLARE LineX, LineY, LineZ : STRING
LineX ← ""
LineY ← ""
LineZ ← ""
OPENFILE FileName FOR READ
WHILE NOT EOF(FileName) DO
LineX ← LineY
LineY ← LineZ
READFILE FileName, LineZ
ENDWHILE
CLOSEFILE FileName
OUTPUT LineX
OUTPUT LineY
OUTPUT LineZ
ENDPROCEDURE
- Mỗi dòng mới đẩy các dòng trước đó đi, nên tại
EOFba biến chứa ba dòng cuối; tệp ngắn hơn sẽ xuất chuỗi rỗng. Đối với năm dòng đầu, đếm số lần đọc và dừng lại ở năm hoặc ởEOF, tùy cái nào xảy ra trước. Tệp rỗng khiếnEOFtrở thành true ngay sau khi mở.
Sắp xếp các bước của thủ tục LastLines theo thứ tự.
Difficulty 3/5 · 200 coins + a small bonus on first completion today
Khởi tạo, mở, lặp với việc dịch trước khi đọc, đóng, xuất. Dịch sau khi đọc sẽ làm mất dòng mới nhất.
Trường trong một dòng
- Một bản ghi được viết thành một dòng, các trường của nó nối với nhau bởi một ký tự ngăn cách, và mỗi số hoặc Boolean được chuyển đổi với
NUM_TO_STR(và đọc lại vớiSTR_TO_NUM, hoặc bằng cách so sánh với"TRUE"). - Chọn một ký tự phân cách không bao giờ xuất hiện trong dữ liệu: dấu phẩy hoặc
|cho tên và số; không dùng khoảng trắng khi tên có thể chứa nó. - Đọc lại: đọc dòng, tách ra tại ký tự phân cách, chuyển đổi mỗi trường về đúng kiểu dữ liệu, lưu vào bản ghi.

Nối bằng ký tự phân cách để ghi; tách và chuyển đổi để đọc
Một dòng lưu tên đầy đủ và điểm số của người chơi. Phân tách nào là lựa chọn an toàn nhất?
Difficulty 1/5 · 100 coins + a small bonus on first completion today
Phân tách không bao giờ được xuất hiện bên trong một trường. Tên đầy đủ chứa dấu cách, và điểm số chứa chữ số.
Một INTEGER có thể được ghi trực tiếp vào tệp văn bản mà không cần chuyển đổi sang chuỗi trước.
Difficulty 1/5 · 100 coins + a small bonus on first completion today
Tệp văn bản chứa các dòng ký tự. Chuyển đổi bằng NUM_TO_STR để ghi và STR_TO_NUM để đọc lại.
Ví dụ minh họa: lưu một bản ghi, tải lại
- Một bản ghi
Playercó các trườngName : STRINGvàScore : INTEGER. Viết pseudocode để thêm nó vàoscores.txtdưới dạng một dòng, và đọc lại một dòng vào bản ghi.
OPENFILE "scores.txt" FOR APPEND
WRITEFILE "scores.txt", Player.Name & "," & NUM_TO_STR(Player.Score)
CLOSEFILE "scores.txt"
OPENFILE "scores.txt" FOR READ
READFILE "scores.txt", Line
Pos ← POSITION(Line, ",")
Player.Name ← LEFT(Line, Pos - 1)
Player.Score ← STR_TO_NUM(MID(Line, Pos + 1, LENGTH(Line) - Pos))
CLOSEFILE "scores.txt"
- Điểm số: chế độ đúng, chuyển đổi số theo cả hai chiều, ký tự phân cách không xuất hiện trong tên, và cả hai tệp đều đóng.
Để lưu một bản ghi thành một dòng của tệp văn bản, chương trình phải: chọn tất cả các đáp án đúng.
Difficulty 2/5 · 140 coins + a small bonus on first completion today
Chuyển đổi, ghép, viết, đóng. Tệp văn bản không có bố trí nhị phân; đó là những gì tệp nhị phân sẽ làm.
Truy cập tuần tự và truy cập trực tiếp
- Tệp văn bản là tuần tự (tương tự): nó được đọc theo thứ tự từ đầu, vì vậy việc tìm thấy một dòng đòi hỏi phải đọc tất cả các dòng trước đó.
- Truy cập trực tiếp (ngẫu nhiên) nhảy ngay đến một bản ghi ở vị trí đã tính toán mà không cần đọc các bản ghi khác; nó yêu cầu các bản ghi có độ dài cố định, điều mà tệp văn bản không có.
- Đối với chương trình học, vòng lặp tệp văn bản trên là mô hình: mở, kiểm tra
EOF, đọc, đóng.
Truy cập trực tiếp (ngẫu nhiên) cho phép chương trình nhảy thẳng đến một bản ghi mà không cần đọc các bản ghi khác trước.
Difficulty 1/5 · 100 coins + a small bonus on first completion today
Truy cập tuần tự phải đọc từ đầu.
Điểm số dễ mất
- Đọc vượt quá cuối file. Kiểm tra
EOFtrước mỗi lầnREADFILE. - Mở
FOR WRITEkhi tệp phải giữ nguyên nội dung. Đó làAPPEND. - Ghi số mà không
NUM_TO_STR, hoặc đọc lại mà khôngSTR_TO_NUM. Tệp văn bản chỉ chứa chuỗi. - Unforgotten
CLOSEFILE, or using a file beforeOPENFILE. Both lose the mark for the file handling.
Bạn đã nắm vững
- Tệp cung cấp sự bền vững: dữ liệu tồn tại sau khi chương trình kết thúc, có thể được chia sẻ, và có thể vượt quá bộ nhớ
OPENFILE … FOR READ | WRITE | APPEND→READFILE/WRITEFILE→CLOSEFILE;WRITEghi đè,APPENDthêm vào cuối- Kiểm tra
EOFtrước mỗi lần đọc; chuyển đổi số vớiNUM_TO_STRra ngoài vàSTR_TO_NUMquay trở lại - một bản ghi = một dòng, các trường được nối bởi một ký tự phân cách không bao giờ xuất hiện trong dữ liệu