Часть моей программы имеет два возможных случая: (1) если пользователь дает только 2 аргумента командной строки, принимает ввод со стандартного ввода (cin) (2) если пользователь дает 3 аргумента командной строки (последний из которых является именем файла ), получить ввод из файла. Чтобы не использовать повторно один и тот же код для обоих вариантов, я попытался использовать указатель на суперкласс как cin, так и ifstream, istream для обоих средств ввода.
Моя проблема в том, что в строках 5 и 22 кода ниже я пытаюсь сослаться на методы, доступные только для подкласса ifstream (открыть и закрыть). Исходя из моей логики, если вызываются эти методы, указатель должен указывать на тип ifstream, но программа не компилируется, потому что эти методы не определены в классе istream.
Есть ли способ обойти это?
istream *currentStream;
if (argc == 3) {
// Handle optional file input
currentStream = new ifstream(argv[2]);
currentStream->open(argv[2]);
if (currentStream->fail()) {
cerr << "FILE COULD NOT BE OPENED\n";
return 1;
}
} else {
currentStream = &cin;
}
string myLine;
// go line by line and translate it
while (getline(*currentStream, myLine)) {
if (currentStream->eof()) {
break;
}
cout << rot13(myLine) << endl;
}
if (dynamic_cast<ifstream*>(currentStream)) {
currentStream->close();
}
// handle pointer
delete currentStream;
currentStream = NULL;
return 0;
open
иclose
, а класс безifstream
просто ничего не делал бы, а другой класс фактически открывал и закрывал быifstream
. У вас правильная идея сdynamic_cast
, но вы должны получить возврат, подобныйif (ifstream* filestream = dynamic_cast...) { filestream->close()
- person Tas   schedule 26.09.2019std::ifstream
, он сам вызоветopen
. И вызовclose
не нужен, потому что его вызовет деструкторstd::ifstream
. Это оставляет одну истинную проблему:delete currentStream;
- это неопределенное поведение, когдаargc != 3
из-за попыткиdelete &cin
. - person Algirdas Preidžius   schedule 26.09.2019