D'après la réponse d'Éric Malenfant:
AFAIK, il n'y a aucun moyen de le faire en C ++ standard. Selon votre plate-forme, votre implémentation de la bibliothèque standard peut offrir (en tant qu'extension non standard) un constructeur fstream prenant un descripteur de fichier en entrée. (C'est le cas de libstdc ++, IIRC) ou d'un FILE *.
Sur la base des observations ci-dessus et de mes recherches ci-dessous, il existe un code de travail en deux variantes; un pour libstdc ++ et un autre pour Microsoft Visual C ++.
libstdc ++
Il existe un __gnu_cxx::stdio_filebuf
modèle de classe non standard qui hérite std::basic_streambuf
et a le constructeur suivant
stdio_filebuf (int __fd, std::ios_base::openmode __mode, size_t __size=static_cast< size_t >(BUFSIZ))
avec description Ce constructeur associe un tampon de flux de fichiers à un descripteur de fichier POSIX ouvert.
Nous le créons en passant le handle POSIX (ligne 1) puis nous le passons au constructeur d'istream en tant que basic_streambuf (ligne 2):
#include <ext/stdio_filebuf.h>
#include <iostream>
#include <fstream>
#include <string>
using namespace std;
int main()
{
ofstream ofs("test.txt");
ofs << "Writing to a basic_ofstream object..." << endl;
ofs.close();
int posix_handle = fileno(::fopen("test.txt", "r"));
__gnu_cxx::stdio_filebuf<char> filebuf(posix_handle, std::ios::in); // 1
istream is(&filebuf); // 2
string line;
getline(is, line);
cout << "line: " << line << std::endl;
return 0;
}
Microsoft Visual C ++
Il y avait une version non standard du constructeur d'ifstream prenant le descripteur de fichier POSIX, mais il manque à la fois dans la documentation actuelle et dans le code. Il existe une autre version non standard du constructeur d'ifstream prenant FILE *
explicit basic_ifstream(_Filet *_File)
: _Mybase(&_Filebuffer),
_Filebuffer(_File)
{ // construct with specified C stream
}
et ce n'est pas documenté (je n'ai même pas pu trouver de documentation ancienne où il serait présent). Nous l'appelons (ligne 1) avec le paramètre résultant de l'appel de _fdopen pour obtenir le flux C FILE * à partir du descripteur de fichier POSIX.
#include <cstdio>
#include <iostream>
#include <fstream>
#include <string>
using namespace std;
int main()
{
ofstream ofs("test.txt");
ofs << "Writing to a basic_ofstream object..." << endl;
ofs.close();
int posix_handle = ::_fileno(::fopen("test.txt", "r"));
ifstream ifs(::_fdopen(posix_handle, "r")); // 1
string line;
getline(ifs, line);
ifs.close();
cout << "line: " << line << endl;
return 0;
}