In C, how to I get to a specified directory?
I have to do a program where I need to index the files in a specified directory. I've gotten the indexing part down, but what I'm having trouble with is how to navigate to the directory. For example, say when I start the program, it will ask "What directory would you like to index," And then the input would be "usr/Documents/CS/Assignment4," how do I get to the "Assignment4" directory? I know recursion is needed, but I'm really confused as to how directories work in C. Say my source file is in "usr/Documents/SourceCode," then what should I do to get to Assignment4?
I know I sound like I want all the answers, but I'm completely lost as to how directories work, and the book I have sucks. So even if all you have is a link to a good tutorial on this, that would be fantastic.
I'm running Linux, Ubuntu 开发者_高级运维to be exact. GCC is the compiler.
The C programming language doesn't have a notion of a file system. This is instead an operating system specific question.
Based on the style of directory in your question though it sounds like you're on a unix / linux style system. If that's the case then you're looking for the opendir
function
- http://linux.die.net/man/3/opendir
Recursively traversing a directory in C goes something like this:
Use opendir
and readdir
to list the directory entries. I probably shouldn't be doing this, but I'm posting a full code sample (sans error handling) because there are a bunch of little things you have to do to ensure you're using the API correctly:
DIR *dir;
struct dirent *de;
const char *name;
dir = opendir(dirpath);
if (dir == NULL) {
/* handle error */
}
for (;;) {
errno = 0;
de = readdir(dir);
if (de == NULL) {
if (errno != 0) {
/* handle error */
} else {
/* no more entries left */
break;
}
}
/* name of file (prefix it with dirpath to get a usable file path) */
name = de->d_name;
/* ignore . and .. */
if (name[0] == '.' && (name[1] == '\0' || (name[1] == '.' && name[2] == '\0')))
continue;
/* do something with the file */
}
if (closedir(dir) != 0) {
/* handle error */
}
When working with each file, be sure to prepend the dirpath to it (along with a slash, if needed). You could also use chdir
to descend and ascend, but it introduces complications in practice (e.g. you can't traverse two directories simultaneously), so I personally recommend keeping your current working directory stationary and using string manipulation to concatenate paths.
To find out if a path is a directory or not (and hence whether you should opendir()
it), I recommend using lstat()
rather than stat()
, as the latter follows symbolic links, meaning your directory traversal could get caught in a loop and you'll end up with something like this ctags output.
Of course, since directory structure is recursive in nature, recursion plays a natural role in the traversal process: make a recursive call when a child path is a directory.
The name of the directory is only a string.
So opendir("filename"); will make it possible to read the directory "file".
However you should perhaps start thinking in filenames and pathes.
"usr/Documents/SourceCode" + "/../CS/Assignment4" is the same as "usr/Documents/CS/Assignment4" however I assume you are missing the leading "/".
Well, I don't get how you can be lost how directories work. A directory is nothing different than a "folder" in Windows or in Mac OS X. Bottom line a hard disk has a filesystem and a filesystem only consists out of folders/directories that "contain" files (and special files like named sockets etc., this should not interest you right now).
Hope this helped at least a bit.
Angelo
精彩评论