Sự khác nhau giữa các chế độ a, a +, w, w + và r + trong chức năng mở tích hợp?


610

Trong python built-in mở chức năng, sự khác biệt chính xác giữa các phương thức là gì w, a, w+, a+, và r+?

Cụ thể, tài liệu này ngụ ý rằng tất cả những điều này sẽ cho phép ghi vào tệp và nói rằng nó mở các tệp để "nối thêm", "viết" và "cập nhật" một cách cụ thể, nhưng không xác định các thuật ngữ này có nghĩa gì.


11
Liên kết bạn cung cấp xác định chính xác các giá trị. Phần nào về liên kết bạn cung cấp mà bạn không thể nhìn thấy hoặc không hiểu? Bạn có thể làm rõ câu hỏi của bạn để giải thích những gì bạn không hiểu về liên kết?
S.Lott

@ChrisB. - Tôi đã báo cáo đây là lỗi tại bug.python.org/su19627
Bulwersator

2
không có tài liệu đơn giản và duy nhất giải thích ý nghĩa của dấu +?
Charlie Parker

Câu trả lời:


740

Các chế độ mở là hoàn toàn giống như đối với các chức năng thư viện chuẩn C fopen().

Các BSD fopenmanpage định nghĩa chúng như sau:

 The argument mode points to a string beginning with one of the following
 sequences (Additional characters may follow these sequences.):

 ``r''   Open text file for reading.  The stream is positioned at the
         beginning of the file.

 ``r+''  Open for reading and writing.  The stream is positioned at the
         beginning of the file.

 ``w''   Truncate file to zero length or create text file for writing.
         The stream is positioned at the beginning of the file.

 ``w+''  Open for reading and writing.  The file is created if it does not
         exist, otherwise it is truncated.  The stream is positioned at
         the beginning of the file.

 ``a''   Open for writing.  The file is created if it does not exist.  The
         stream is positioned at the end of the file.  Subsequent writes
         to the file will always end up at the then current end of file,
         irrespective of any intervening fseek(3) or similar.

 ``a+''  Open for reading and writing.  The file is created if it does not
         exist.  The stream is positioned at the end of the file.  Subse-
         quent writes to the file will always end up at the then current
         end of file, irrespective of any intervening fseek(3) or similar.

3
Tôi tin rằng bạn có nghĩa là cuộc gọi fopen trong thư viện chuẩn C (không phải là cuộc gọi hệ thống)
Eli Courtwright

14
LƯU Ý: Python v3 thêm một số chế độ bổ sung. liên kết đến tài liệu
Alex

5
Lưu ý rằng ww+cả hai đều có thể làmThe file is created if it does not exist
Wei Yang

4
Trên Windows, bnối vào chế độ mở file trong chế độ nhị phân, vì vậy cũng có những chế độ như rb, wb, và r+b. Python trên Windows phân biệt giữa các tệp văn bản và tệp nhị phân; các ký tự cuối dòng trong tệp văn bản sẽ tự động được thay đổi một chút khi dữ liệu được đọc hoặc ghi.

6
Tôi có đúng không khi nói rằng +không làm điều gì đó độc lập nhất quán nếu có a, whay r? Hay tôi không nhìn thấy mô hình? Mô hình là gì?
Charlie Parker

510

Tôi nhận thấy rằng thỉnh thoảng tôi cần Google fopen một lần nữa, chỉ để xây dựng một hình ảnh tinh thần về sự khác biệt chính giữa các chế độ là gì. Vì vậy, tôi nghĩ rằng một sơ đồ sẽ nhanh hơn để đọc lần sau. Có lẽ người khác cũng sẽ thấy hữu ích.


3
Các amô tả là sai . Các bài viết luôn được định vị ở cuối.
Antti Haapala

10
@ Và tôi tin rằng @Antti đang đề cập đến tài sản Subsequent writes to the file will always end up at the then current end of file, irrespective of any intervening fseek(3) or similarcó phần mạnh mẽ hơn là chỉ nói vị trí ban đầu là kết thúc.
jcai

8
@CharlieParker Về cơ bản có hai thao tác tệp (đọc, ghi). Chế độ r chủ yếu để đọc, chế độ w , a chủ yếu để viết. Và dấu cộng cho phép thao tác thứ hai cho một chế độ nhất định (nói đơn giản).
Jeyekomon

22
Đối với hậu thế: cắt ngắn có nghĩa là ghi đè từ đầu.
Minh Trần

4
@Jeyekomon Tóm tắt của bạn trong nhận xét của bạn ở đây có lẽ là điều hữu ích nhất mà tôi đã đọc khi cố gắng tìm hiểu về các chế độ này theo cách mà bây giờ tôi có thể nhớ! Biểu đồ dòng chảy trong câu trả lời này rất hay và bảng trong câu trả lời dưới đây rất hay, nhưng nếu những câu trả lời này (và những câu trả lời khác) bắt đầu với điểm đơn giản này và hoạt động từ đó, nó sẽ giúp cung cấp một khung tinh thần tốt hơn để treo các chi tiết trên. Cảm ơn (Tôi biết điều này có thể nằm trên đường biên giới của spam, nhưng tôi cảm thấy nhận xét của bạn xứng đáng được thừa nhận)
Tim

206

Cùng một thông tin, chỉ ở dạng bảng

                  | r   r+   w   w+   a   a+
------------------|--------------------------
read              | +   +        +        +
write             |     +    +   +    +   +
write after seek  |     +    +   +
create            |          +   +    +   +
truncate          |          +   +
position at start | +   +    +   +
position at end   |                   +   +

trong đó ý nghĩa là: (chỉ để tránh giải thích sai)

  • đọc - đọc từ tập tin được cho phép
  • ghi - ghi vào tập tin được cho phép

  • tạo - tập tin được tạo nếu nó chưa tồn tại

  • dấu chấm câu - trong khi mở tệp, nó được làm trống (tất cả nội dung của tệp bị xóa)

  • vị trí bắt đầu - sau khi tệp được mở, vị trí ban đầu được đặt thành bắt đầu của tệp

  • vị trí ở cuối - sau khi tệp được mở, vị trí ban đầu được đặt ở cuối tệp

Lưu ý: aa+luôn luôn nối vào cuối tệp - bỏ qua mọi seekchuyển động.
BTW. hành vi thú vị ít nhất là trên win7 / python2.7 của tôi, đối với tệp mới được mở trong a+chế độ:
write('aa'); seek(0, 0); read(1); write('b')- giây writebị bỏ qua
write('aa'); seek(0, 0); read(2); write('b')- lần writetăng thứ haiIOError


10
Tại sao không có "Tạo tệp nếu nó không tồn tại. Nếu nó tồn tại, vị trí khi bắt đầu, cho phép đọc và ghi"? Đây là trường hợp sử dụng rõ ràng nhất đối với tôi: Tôi đang lưu trữ dữ liệu trong một tệp. Nếu tập tin không có ở đó, hãy tạo nó thay vì lỗi. Nếu có dữ liệu trong tệp tôi muốn đọc tất cả từ đầu, hãy cập nhật một số nội dung sau đó viết lại hoàn toàn tệp từ 0 cho THỜI GIAN TIẾP THEO tôi tải nó. Tôi sử dụng open(file,'a'); close(); open(file,'r+')để thực hiện điều này.
đầu

2
"Cắt ngắn" có nghĩa là gì trong bối cảnh này?
Charlie Parker

3
@CharlieParker Điều đó có nghĩa là tất cả nội dung của tệp bị xóa (tệp bị bỏ trống)
ngành công

1
Bạn có thể muốn thêm một lưu ý rằng với aa+ghi sẽ luôn xảy ra ở cuối tệp, bất kể người ta có di chuyển con trỏ bằng tay hay không seek().
balu

1
Còn việc cập nhật bảng, bao gồm 'x' cho Python 3 thì sao?
Nikos Alexandris

39

Các tùy chọn giống như đối với hàm fopen trong thư viện chuẩn C:

w cắt ngắn tập tin, ghi đè bất cứ điều gì đã có

a nối vào tập tin, thêm vào bất cứ điều gì đã có

w+ mở để đọc và viết, cắt bớt tệp nhưng cũng cho phép bạn đọc lại những gì đã được ghi vào tệp

a+ mở để nối và đọc, cho phép cả hai bạn thêm vào tệp và cũng đọc nội dung của nó


2
"Cắt ngắn" có nghĩa là gì trong bối cảnh này? Có nghĩa là xóa dữ liệu cũ nếu nó có một số? Hoặc một cái gì đó cụ thể hơn?
Charlie Parker

3
@CharlieParker: Chính xác - điều đó có nghĩa là tất cả dữ liệu trong tệp hiện có sẽ bị hủy và chúng tôi bắt đầu viết từ đầu tệp trống.
Eli Courtwright

9

Tôi nghĩ rằng điều này rất quan trọng để xem xét thực hiện đa nền tảng, tức là dưới dạng CYA. :)

Trên Windows, 'b' được thêm vào chế độ sẽ mở tệp ở chế độ nhị phân, do đó, cũng có các chế độ như 'rb', 'wb' và 'r + b'. Python trên Windows phân biệt giữa các tệp văn bản và tệp nhị phân; các ký tự cuối dòng trong tệp văn bản sẽ tự động được thay đổi một chút khi dữ liệu được đọc hoặc ghi. Điều chỉnh hậu trường này đối với dữ liệu tệp là tốt đối với các tệp văn bản ASCII, nhưng nó sẽ làm hỏng dữ liệu nhị phân như trong các tệp JPEG hoặc EXE. Hãy thật cẩn thận khi sử dụng chế độ nhị phân khi đọc và ghi các tệp như vậy. Trên Unix, việc nối thêm 'b' vào chế độ sẽ không ảnh hưởng gì, vì vậy bạn có thể sử dụng nó độc lập với nền tảng cho tất cả các tệp nhị phân.

Này được trích dẫn trực tiếp từ Python Software Foundation 2.7.x .


9

Tôi nhấn vào điều này khi cố gắng tìm hiểu lý do tại sao bạn sẽ sử dụng chế độ 'w +' so với 'w'. Cuối cùng, tôi chỉ làm một số thử nghiệm. Tôi không thấy nhiều mục đích cho chế độ 'w +', vì trong cả hai trường hợp, tệp bị cắt ngắn để bắt đầu. Tuy nhiên, với 'w +', bạn có thể đọc sau khi viết bằng cách tìm kiếm lại. Nếu bạn đã thử đọc bất kỳ với 'w', nó sẽ tăng IOError. Đọc mà không sử dụng tìm kiếm với chế độ 'w +' sẽ không mang lại kết quả gì, vì con trỏ tệp sẽ ở sau nơi bạn đã viết.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.