AutoCAD 3DMAX C语言 Pro/E UG JAVA编程 PHP编程 Maya动画 Matlab应用 Android
Photoshop Word Excel flash VB编程 VC编程 Coreldraw SolidWorks A Designer Unity3D
 首页 > Linux

Linux下C语言编程--文件的操作

51自学网 http://www.wanshiok.com



3:目录文件的操作
在我们编写程序的时候,有时候会要得到我们当前的工作路径。C库函数提供了getcwd来解决这个问题。
#include

char *getcwd(char *buffer,size_t size);

我们提供一个size大小的buffer,getcwd会把我们当前的路径考到buffer中.如果buffer太小,函数会返回-1和一个错误号.
Linux提供了大量的目录操作函数,我们学习几个比较简单和常用的函数.
#include
#include
#include
#include
#include

int mkdir(const char *path,mode_t mode);
DIR *opendir(const char *path);
struct dirent *readdir(DIR *dir);
void rewinddir(DIR *dir);
off_t telldir(DIR *dir);
void seekdir(DIR *dir,off_t off);
int closedir(DIR *dir);

struct dirent {
long d_ino;
off_t d_off;
unsigned short d_reclen;
char d_name[NAME_MAX+1]; /* 文件名称 */

mkdir很容易就是我们创建一个目录,opendir打开一个目录为以后读做准备.readdir读一个打开的目录.rewinddir是用来重读目录的和我们学的rewind函数一样.closedir是关闭一个目录.telldir和seekdir类似与ftee和fseek函数.
下面我们开发一个小程序,这个程序有一个参数.如果这个参数是一个文件名,我们输出这个文件的大小和最后修改的时间,如果是一个目录我们输出这个目录下所有文件的大小和修改时间.

#include
#include
#include
#include
#include
#include
#include

static int get_file_size_time(const char *filename)
{
struct stat statbuf;

if(stat(filename,&statbuf)==-1)
{
printf("Get stat on %s Error:%s/n",
filename,strerror(errno));
return(-1);
}

if(S_ISDIR(statbuf.st_mode))return(1);
if(S_ISREG(statbuf.st_mode))
printf("%s size:%ld bytes/tmodified at %s",
filename,statbuf.st_size,ctime(&statbuf.st_mtime));

return(0);
}

int main(int argc,char **argv)
{
DIR *dirp;
struct dirent *direntp;
int stats;

if(argc!=2)
{
printf("Usage:%s filename/n/a",argv[0]);
exit(1);
}

if(((stats=get_file_size_time(argv[1]))==0)||(stats==-1))exit(1);

if((dirp=opendir(argv[1]))==NULL)
{
printf("Open Directory %s Error:%s/n",
argv[1],strerror(errno));
exit(1);
}

while((direntp=readdir(dirp))!=NULL)
if(get_file_size_time(direntp-br> closedir(dirp);
exit(1);
}


4:管道文件
Linux提供了许多的过滤和重定向程序,比如more cat
等等.还提供了< > | <<等等重定向操作符.在这些过滤和重 定向程序当中,都用到了管道这种特殊的文件.系统调用pipe可以创建一个管道.
#include

int pipe(int fildes[2]);

pipe调用可以创建一个管道(通信缓冲区).当调用成功时,我们可以访问文件描述符fildes[0],fildes[1].其中fildes[0]是用来读的文件描述符,而fildes[1]是用来写的文件描述符.
在实际使用中我们是通过创建一个子进程,然后一个进程写,一个进程读来使用的.
关于进程通信的详细情况请查看进程通信

#include
#include
#include
#include
#include
#include
#include
#define BUFFER 255

int main(int argc,char **argv)
{
char buffer[BUFFER+1];
int fd[2];

if(argc!=2)
{
fprintf(stderr,"Usage:%s string/n/a",argv[0]);
exit(1);
}

if(pipe(fd)!=0)
{
fprintf(stderr,"Pipe Error:%s/n/a",strerror(errno));
exit(1);
}
if(fork()==0)
{
close(fd[0]);
printf("Child[%d] Write to pipe/n/a",getpid());
snprintf(buffer,BUFFER,"%s",argv[1]);
write(fd[1],buffer,strlen(buffer));
printf("Child[%d] Quit/n/a",getpid());
exit(0);
}
else
{
close(fd[1]);
printf("Parent[%d] Read from pipe/n/a",getpid());
memset(buffer,'/0',BUFFER+1);
read(fd[0],buffer,BUFFER);
printf("Parent[%d] Read:%s/n",getpid(),buffer);
exit(1);
}
}

为了实现重定向操作,我们需要调用另外一个函数dup2.
#include

int dup2(int oldfd,int newfd);

dup2将用oldfd文件描述符来代替newfd文件描述符,同时关闭newfd文件描述符.也就是说,
所有向newfd操作都转到oldfd上面.下面我们学习一个例子,这个例子将标准输出重定向到一个文件.

#include
#include
#include
#include
#include
#include
#include

#define BUFFER_SIZE 1024

int main(int argc,char **argv)
{
int fd;
char buffer[BUFFER_SIZE];

if(argc!=2)
{
fprintf(stderr,"Usage:%s outfilename/n/a",argv[0]);
exit(1);
}

if((fd=open(argv[1],O_WRONLY|O_CREAT|O_TRUNC,S_IRUSR|S_IWUSR))==-1)
{
fprintf(stderr,"Open %s Error:%s/n/a",argv[1],strerror(errno));
exit(1);
}

if(dup2(fd,STDOUT_FILENO)==-1)
{
fprintf(stderr,"Redirect Standard Out Error:%s/n/a",strerror(errno));
exit(1);
}

fprintf(stderr,"Now,please input string");
fprintf(stderr,"(To quit use CTRL+D)/n");
while(1)
{
fgets(buffer,BUFFER_SIZE,stdin);
if(feof(stdin))break;
write(STDOUT_FILENO,buffer,strlen(buffer));
}
exit(0);
}

好了,文件一章我们就暂时先讨论到这里,学习好了文件的操作我们其实已经可以写出一些比较有用的程序了.我们可以编写一个实现例如dir,mkdir,cp,mv等等常用的文件操作命令了.
想不想自己写几个试一试呢?

 
 

上一篇:Linux教程(30)-vi命令(4)  下一篇:Linux下C语言编程--进程的创建