Почему «ifstream» и «ofstream» добавляются к std, тогда как «fstream» может служить обеим целям?

С помощью std::fstream можно объявлять объекты обоих типов ifstream и ofstream. Единственная разница в том, что с fstream нам нужно предоставить in, out, app в качестве параметра, который может не всегда требоваться для двух других.

Есть ли в ifstream,ofstream что-то особенное, чего нельзя добиться с помощью fstream, или это просто удобство кодирования?


person iammilind    schedule 02.08.2012    source источник


Ответы (3)


Это немного похоже на вопрос, зачем нам const, когда вы все равно можете читать и писать из переменных. Это позволяет проверять время компиляции, бесценную функцию для уменьшения количества ошибок. Это также более самодокументируемо, так как при просмотре объявления без вызова конструктора вы можете увидеть, является ли это вводом, выводом или и тем, и другим: параметры, которые вы упоминаете, часто можно увидеть только в файле реализации, который может не быть под рукой. Кроме того, каждый тип потока может иметь несколько различий в элементах данных, которые им нужны - потенциально использование минимально функционального класса, соответствующего вашим фактическим потребностям, может сэкономить память, инициализацию времени или проверку этих других переменных и т. д.

person Tony Delroy    schedule 02.08.2012

Во всяком случае, fstream — это просто удобство. В частности, у вас есть в основном:

namespace std { 
class ifstream { /* ... */ };

class ofstream { /* ... */ };

class fstream : public ifstream, public ofstream { /* ... */ };
}

[очевидно, пропуская множество несущественных деталей].

Короче говоря, fstream обеспечивает все входные возможности ifstream и все выходные возможности ofstream, производные как от ifstream, так и от ofstream. Без ifstream и ofstream fstream (по крайней мере, во всем, что напоминает его нынешнюю форму) вообще не могло бы существовать.

person Jerry Coffin    schedule 02.08.2012
comment
Одна несущественная деталь, которую вы пропустили, это фактическая ошибка. fstream (фактически basic_fstream‹char›) не наследуется ни от ifstream, ни от ofstream. - person DanielKO; 02.08.2012
comment
@DanielKO: Верно, но да, действительно не имеет значения. Если вы хотите получить техническую информацию, ifstream происходит от istream, а ofstream происходит от ostream. fstream является производным от iostream, который является производным от istream и ostream (и да, конечно, чтобы быть технически правильным, у нас должны быть разбросаны различные префиксы std:: и basic_ и суффиксы <char>). Вы действительно считаете, что исключение деталей, которые даже вы признаете несущественными, является надежным основанием для отрицательного голосования? - person Jerry Coffin; 02.08.2012
comment
Но вы подразумеваете, что fstream тривиально наследует реализации как ifstream, так и ofstream, как если бы fstream был просто клеем двух других. Вы не должны упрощать свой ответ до такой степени, что он не отражает факты. Я забыл процитировать не относящуюся к делу деталь, чтобы подчеркнуть сарказм, извините за это. - person DanielKO; 02.08.2012
comment
@DanielKO: Можете ли вы указать на что-нибудь важное, что на самом деле потеряно при упрощении? Реальность такова, что fstream это довольно тривиально, и да, это просто клей. Худшее, что вы можете сказать, это то, что клей работает немного в другом направлении, в основном приклеивая iostream к входным и выходным буферам файлового потока вместо того, чтобы переходить к ifstream и ofstream как таковым. Вхождение в это удлиняет ответ (чрезвычайно), не добавляя по существу ничего важного. Посредник iostream в основном интересен как основа для других классов (например, stringstream). - person Jerry Coffin; 02.08.2012
comment
Конечно. void foo(std::ofstream& output); void bar() { std::fstream f("a"); foo(f); } - person DanielKO; 03.08.2012
comment
@DanielKO: и как это связано с тем, предоставляют ли ifstream и/или ofstream что-нибудь полезное и/или должны ли они существовать? - person Jerry Coffin; 03.08.2012

Весь смысл в том, чтобы быть универсальным. Если вам нужно только прочитать файл, вы можете взять ifstream в качестве параметра, и тогда все, что поддерживает чтение, может быть передано, даже если оно недоступно для записи. Наоборот.

person Antimony    schedule 02.08.2012
comment
Я вообще не понимаю, как этот ответ относится к вопросу. - person ildjarn; 02.08.2012
comment
@Tony Да, я только что заметил, что ifstream вынужден предоставлять объект filebuf, ограничивая возможности альтернативных реализаций. Я думаю, что проверка времени компиляции и самодокументирование - лучшее объяснение. - person Antimony; 02.08.2012