Click to See Complete Forum and Search --> : Reading in files without knowing the filenames beforehand?


C++ Newbie
January 20th, 2003, 11:14 AM
Hi,

I have to write a program where I am given an input directory which will contain files with known extensions (e.g., *.exd, *.txt) but of which I do not know the beginnings of the names. Anyway, I have to be able to automatically detect all such files and then open them one by one. Can someone help me out how I can accomplish this? I know how to open a file when I know the entire name beforehand but have never had to do this before.

For example, lets say the directory contains the following files:

genseq001.txt
Data set 2.exd
Data set 2 jeff.exd
Data set 31 steve.exd
genseq002.txt
logref.txt
output.exf
output1.exf

So in this case, I have to be able to figure out that all these files are in the directory and then process them one by one except for the *.exf files.

Any help on what classes or commands I can use? I have to use standard C++ so it works on both Windows and Linux.

Thanks!

DanM
January 20th, 2003, 11:26 AM
I don't know of a portable way to achieve this.
For Windows, you can use FindFirstFile (do a search on the message board - there are a lot of references to it):

http://www.codeguru.com/forum/showthread.php?s=&threadid=220907&highlight=FindFirstFIle

scandir may work for Linux:

http://nodevice.com/sections/ManIndex/man1383.html

Dan

zach
January 21st, 2003, 04:38 AM
To be portable you need an OS abstraction layer. Some libraries like ACE provides this. It is however intended for large scale programs and middleware. So it's like shooting birds with a bazooka.

mohini sathe
January 21st, 2003, 05:02 AM
struct _finddata_t c_file;//for retrieving map file attributes.
FILE* fpTemp = NULL ;
long hFile = 0L;
if( (hFile = _findfirst( "*.exd", &c_file )) == -1L )
{
cout << "*.exd files not found ! "<< argv[1] << endl;
return;
}
else
{
do
{
//This way u can open and read the files one by one without knowing the filename
fpTemp = fopen(c_file.name);
//if _findnext function returns -1 try for another ext
} while( _findnext( hFile, &c_file ) == 0 );
_findclose( hFile );//in the end close the handle.
}
With few manipulation in the above code, u can have complement logic for opening
all files except the mentioned files.

But here _findfirst searches the files in the default directory.
You have to set the dirsctory path b4 calling _findnext function.

DanM
January 21st, 2003, 09:52 AM
If you look at the Compatibility section of the MSDN documentation for _findfirst/_findnext you can see that it says only Win95/WinNT without any mention of ANSI so these functions are not usable on other platforms.
They are MS specific...

http://msdn.microsoft.com/library/default.asp?url=/library/en-us/vccore98/html/_crt__findfirst.2c_._findfirsti64.2c_._wfindfirst.2c_._wfindfirsti64.asp

Dan

Paul McKenzie
January 21st, 2003, 10:25 AM
Originally posted by C++ Newbie
Hi,

I have to write a program where I am given an input directory which will contain files with known extensions (e.g., *.exd, *.txt) but of which I do not know the beginnings of the names. Anyway, I have to be able to automatically detect all such files and then open them one by one. Can someone help me out how I can accomplish this?=
For Windows --> FindFirstFile() / FindNextFile()
For Linux --> opendir() / readdir()
For any other OS -- read your compiler's manual.

Basically reading a directory's entries is not only OS specific, it can also be compiler specific. For example, I remember the Borland compiler's version of finding files was dos_findfirst and dos_findnext, while Microsofts was findfirst and findnext. Another compiler may call it something else.

To make it portable, you have to write (or use) two sets of code, one for Windows, the other for Linux and maintain both sets of code. How you maintain it (whether you use #ifdef WINDOWS / #ifdef LINUX, or whether you create two sets of source and include the appropriate one in your projects, or some other method), that's up to you.

Regards,

Paul McKenzie

p8mode
January 21st, 2003, 01:00 PM
An excellent cross platform (and compiler) library which makes such directory reading a sinch is the still well kept secret Qt. This is what KDE use for Linux. See www.trolltech.com where you can download for free the latest version of the library for Unix/Linux. A slightly older version (but still with the functionality youre looking for,. and much more) is also available for free for Windows as a precompiled dll.
By the way, I have nothing to do with Trolltech..my comments are objective!