2012-10-17 38 views
12

thể trùng lặp:
C++ Filehandling: Difference between ios:app and ios:ate?Sự khác nhau giữa ios :: app và ios :: ăn

sự khác biệt giữa các chế độ mở hai tập tin là gì?

ios: ate đặt vị trí con trỏ get/put ở cuối tệp => đọc/ghi sẽ bắt đầu từ kết thúc, nhưng nó khác với ứng dụng ios ::, mở lại tệp ở chế độ chắp thêm như thế nào ... nhưng khi tôi đã tạo ra một dòng suối và mở nó trong chế độ ứng dụng ios: thì con trỏ đưa dòng vẫn trỏ tới điểm bắt đầu, công việc phụ thêm như thế nào?

Ngoài ra tôi hiểu rằng ifstream, ofstream và fstream là các lớp cấp cao để quản lý bộ đệm luồng cơ bản. Vì vậy, nó có nghĩa là ngay cả trong ios: chế độ ứng dụng tôi có thể đọc dữ liệu từ một tập tin?

+1

Về cơ bản 'ứng dụng' luôn tìm cách kết thúc trước khi viết bất kỳ thứ gì, trong khi' ate' cho phép bạn tìm kiếm sau khi mở và giữ nó ở đó. Xem [câu hỏi này] (http://stackoverflow.com/questions/10359702/c-filehandling-difference-between-iosapp-and-iosate). – chris

Trả lời

23

app xuất phát từ 'append'- tất cả đầu ra sẽ được thêm (được nối thêm) vào cuối tệp. Nói cách khác, bạn không thể viết bất cứ nơi nào khác trong tệp nhưng ở cuối

ate có dạng 'ở cuối' - nó đặt vị trí dòng ở cuối tệp khi bạn mở nó nhưng bạn tự do di chuyển nó (tìm kiếm) và viết bất cứ nơi nào nó vui lòng bạn.

+0

Thực tế là 'ate' không ngăn chặn cắt ngắn làm cho nó khá vô dụng. Thực tế là 'ứng dụng' có thể gắn thêm một phần bản ghi vào cuối vào thời điểm không xác định (do đệm) làm cho nó khá vô dụng. –

+0

@James: làm thế nào là 'app' /' ate' bất kỳ khác nhau trong khía cạnh này từ viết vào cuối các tập tin mà * không * mở ra với những lá cờ? Tôi nghĩ đó chỉ là một cách thuận tiện để cứu một người. Tôi đã không nhận ra bất cứ ai mong đợi nó cũng tuôn ra dòng cho họ, hoặc nếu không đảm bảo tính toàn vẹn tập tin. –

+0

@SteveJessop 'app' ánh xạ tới' "a" 'trong' fopen'. Tiêu chuẩn C không yêu cầu atomicity, bởi vì không phải tất cả các hệ thống đều có thể hỗ trợ nó, nhưng _intent_ ban đầu của '" a "' là để triển khai sử dụng cờ 'O_APPEND' khi mở tệp. Điều này làm cho tìm kiếm nguyên tử kết thúc trước mỗi lần viết. Sự khác biệt có thể nhìn thấy nếu các quy trình khác đang ghi vào tệp. Khi một tiến trình khác ghi vào tập tin, vị trí của bạn trong tập tin không tiến lên, và ghi tiếp theo của bạn sẽ ghi đè lên bất cứ điều gì nó đã viết. Với 'ứng dụng', bài viết tiếp theo của bạn sẽ nối thêm, bất kể (và không có chủng tộc). –

8

Nếu bạn nhìn vào ví dụ: this reference, bạn sẽ thấy:

app  seek to the end of stream before each write 

ate  seek to the end of stream immediately after open 

Điều này có nghĩa rằng ios::app chỉ viết ở cuối, nhưng điều đó ios::ate đọc và viết vào cuối theo mặc định. Tuy nhiên, với ios::ate bạn có thể tìm kiếm tự do trong tệp, nhưng với ios::app, bạn sẽ luôn ghi viết ở cuối, bất kể vị trí bạn đặt cho con trỏ viết.

10

ate chỉ đơn giản là vị trí bạn ở cuối tệp sau khi mở và không có gì khác. Nó không được sử dụng nhiều trên một ofstream, ít nhất là không có các cờ khác, vì tập tin sẽ bị cắt ngắn, vì vậy đầu là kết thúc. (Để tránh cắt ngắn, và vẫn có thể viết bất cứ nơi nào trong tập tin, bạn cần hoặc trong ios::in là tốt, ngay cả khi bạn sẽ không đọc.)

app ngăn chặn việc cắt bớt một tập tin hiện có, và khiến mọi chữ viết đi đến cuối tập tin. Về nguyên tắc, nếu có thể; nếu các quy trình khác đang ghi vào cùng một tệp, thì việc viết của bạn vẫn phải đi đến cùng. Tuy nhiên, lưu ý rằng điều này đề cập đến mức ghi hệ thống thực tế. Tuy nhiên, nếu bạn đang viết các dòng nhỏ hơn kích thước bộ đệm và bạn chấm dứt mỗi dòng với std::endl, bạn có thể đếm trên mỗi dòng được nối vào nguyên tử, bất kể các quy trình khác có thể làm gì với tệp. Để có hiệu quả, có thể bạn cũng sẽ muốn sử dụng pubsetbuf trên filebuf để đảm bảo kích thước bộ đệm tối thiểu.

Trong thực tế, tôi không nghĩ rằng mình từng sử dụng một trong số chúng hoặc thấy chúng sử dụng bất kỳ.Các vấn đề đệm với app, đặc biệt, thường dẫn tôi viết streambuf của riêng tôi, với bộ đệm không giới hạn về khái niệm (bộ đệm std::vector<char>), mở tệp hệ thống cơ bản với tương đương app, nhưng đảm bảo chỉ ghi vào nó khi rõ ràng đỏ bừng (như với `std :: endl).

Các vấn đề liên quan