linux:对目录的操作

一、对目录操作

1,打开目标目录 
2.读取目录,,  
3.关闭目录 
目录 当文件看,只不过操作函数和操作文件函数不一样。

*1.opendir

DIR *opendir(const char *name);

功能:打开一个目录获得一个目录流指针
参数:name:目录名
返回值:
    成功返回目录流指针
    失败返回NULL

*2.readdir

struct dirent *readdir(DIR *dirp);
功能:
    从目录流中读取文件信息并将保存信息的结构体
    地址返回
参数:
    dirp:目录流指针
返回值:
    成功时,readdir函数返回一个指向struct dirent结构体的指针,该结构体包含了目录中的一个条目的信息,如文件名、文件类型等。

   出错或者读到目录流末尾返回NULL

*3、closedir

 int closedir(DIR *dirp);
 功能:关闭之前已经打开的目录流对象
 参数:opendir的返回结果中目录流对象
 返回值:成功  0
         失败   -1;

练习:打印当前目录下的信息

#include 
#include 
#include 
#include 
int main(int argc, char *argv[])
{
    DIR * dir = opendir("./");     //使用opendir("./")打开当前目录(.表示当前目录)
    if(NULL == dir)
    {
        fprintf(stderr,"opendir error\n");
        return 1;
    }
    while(1)
    {
        struct dirent * info = readdir(dir);
        if(NULL == info)
        {
            break;
        }
        switch(info->d_type)
        {
            case DT_DIR:
                printf("目录文件 ");
                break;
            case DT_REG:
                printf("普通文件 ");
                break;
            case DT_UNKNOWN:
                printf("其他文件 ");
                break;
            default:
                printf("未知文件 ");
        }
        printf("%s\n",info->d_name);
    }

    closedir(dir);
    return 0;
}

printf("%s\n", info->d_name); 这行代码用于打印出由 readdir() 函数返回的 struct dirent 结构体中 d_name 成员所指向的字符串,即当前目录条目的名称(文件名或子目录名)。

struct dirent 是用于表示目录条目的结构体,它通常包含以下成员(但具体成员可能因系统而异):

  • d_ino:文件的inode号(在某些系统上可能不存在)。
  • d_off:在目录文件中的偏移量(用于内部遍历,通常不对用户程序公开)。
  • d_reclend_name 字段的长度(不包括结尾的null字符),但在现代系统中这个字段可能不再使用。
  • d_type:文件类型(如目录、普通文件等)。
  • d_name:一个以null结尾的字符串,表示目录条目的名称。

二、有关目录的函数

1.chdir  (cd)

chdir ("/home/linux"); "../../"
fopen("1.mp4")

int chdir(const char *path);// /home/linux

功能: 改变当前程序的工作路径
参数:path:改变到的路径
返回值:
    成功返回0
    失败返回-1

2.getcwd (pwd) 

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

功能:获得当前的工作路径
参数:
    buf:保存工作路径空间的首地址
    size:保存路径空间的长度
返回值:
    成功返回包含路径空间的字符串首地址
    失败返回NULL
练习:打印当前目录,打印上一级目录

#include 
#include 
#include 
int main(int argc, char *argv[])
{
    char buf[256]={0};
    getcwd(buf,sizeof(buf));
    printf("current path is %s\n",buf);
    chdir("../");
    getcwd(buf,sizeof(buf));
    printf("change path is %s\n",buf);


    return 0;
}

练习:指定目录下的  .c的文件

#include 
#include 
#include 
#include 
#include 
// ./a.out ../ 
int main(int argc, char *argv[])
{
    if(argc<2)
    {
        fprintf(stdout,"usage:./a.out dirname\n");
        return 1;
    }
    DIR * dir = opendir(argv[1]);
    if(NULL == dir)
    {
        fprintf(stderr,"opendir errpr\n");
        return 1;
    }
    while(1)
    {
        struct dirent * info = readdir(dir);
        if(NULL == info)
        {
            break;
        }
        // .
        if(strlen(info->d_name)>=3)
        {
            t=strlen(info->d_name)
            if(0== strcmp(&info->d_name[t-2],".c"))   //strcmp(&info->d_name[t-2]定位到倒数第二位'.'
            {
                printf("%s\n",info->d_name);
            }
        }
    }

    closedir(dir);
    return 0;
}

3.mkdir 

int mkdir(const char *pathname, mode_t mode);
  • const char *pathname:指向以 null 结尾的字符串的指针,该字符串指定了要创建的目录的路径名。
  • mode_t mode:指定新目录的权限。这些权限由文件模式创建掩码(umask)修改,以限制新目录的权限。如 0666 0777                    mode & ~umask  0002
  • 返回值:
        成功返回0
        失败返回-1

4.rmdir

int rmdir(const char *pathname);

功能:删除一个空目录文件
参数:pathname:目录文件的名字
返回值:
    成功返回0
    失败返回-1

目录中有其他文件时用 rm -fr

*5.stat

int  stat(const  char  *path, struct stat *buf);
功能:
    获得文件的属性
参数:
    path: 文件的路径
    buf:  属性存放空间的首地址
返回值:
    成功返回0
    失败返回-1

struct stat *buf:指向 stat 结构体的指针,该结构体用于存储 path 指定的文件或目录的状态信息。

#include   
#include   
#include   
  
struct stat {  
    dev_t     st_dev;     // 设备ID(文件所在的设备)  
    ino_t     st_ino;     // 节点号(inode号)  
    mode_t    st_mode;    // 文件类型和权限  
    nlink_t   st_nlink;   // 链接数(有多少文件名指向这个节点)  
    uid_t     st_uid;     // 用户ID(文件所有者的用户ID)  
    gid_t     st_gid;     // 组ID(文件所有者的组ID)  
    dev_t     st_rdev;    // 设备类型(如果文件是设备)  
    off_t     st_size;    // 文件大小(以字节为单位)  
    blksize_t st_blksize; // 文件系统I/O的块大小  
    blkcnt_t  st_blocks;  // 分配给文件的块数  
  
    // 以下成员与时间相关  
    time_t    st_atime;   // 最后访问时间  
    time_t    st_mtime;   // 最后修改时间  
    time_t    st_ctime;   // 最后状态改变时间(例如权限或所有权)  
  
    // POSIX.1-2008 增加了以下成员  
    #ifdef _POSIX_C_SOURCE  
    // ... 可能包含额外的成员,如 st_birthtime(文件的创建时间,如果支持)  
    #endif  
};


练习:用stat获取文件信息

#include 
#include 
#include 
#include 
int main(int argc, char *argv[])
{
    struct stat st;
    char filename[]="./01ls.c";
    int ret= stat(filename,&st); 
    if(-1 == ret)
    {
        fprintf(stderr,"stat error\n");
        return 1;
    }

    printf("ino:%lu mode:%d link:%lu uid:%u gid:%u size:%lu time:%lu %s\n",st.st_ino,st.st_mode,st.st_nlink
           ,st.st_uid,st.st_gid,st.st_size,st.st_mtime,filename);

    return 0;
}

st_mode字段是stat结构体的一部分,该结构体通过stat()fstat(), 或 lstat()函数获取文件或目录的状态信息。我们可以通过一系列的宏(定义在头文件中)来访问和操作st_mode字段中的不同部分。

st_mode有32bit,最后9位表示权限,以下表示权限:

           S_IRWXU     00700   owner has read, write, and execute permission

           S_IRUSR     00400   owner has read permission
           S_IWUSR     00200   owner has write permission
           S_IXUSR     00100   owner has execute permission

           S_IRWXG     00070   group has read, write, and execute permission
           S_IRGRP     00040   group has read permission
           S_IWGRP     00020   group has write permission
           S_IXGRP     00010   group has execute permission

           S_IRWXO     00007   others (not in group) have read,  write,  and
                               execute permission
           S_IROTH     00004   others have read permission
           S_IWOTH     00002   others have write permission
           S_IXOTH     00001   others have execute permission

 st_modes的使用:

#include   
#include   
#include   
#include   
#include  // 用于可能的时间格式化,但这里未使用  
  
int main(int argc, char *argv[])  
{  
    struct stat st;  
    char filename[] = "./01ls.c";  
    int ret = stat(filename, &st);  
    if (-1 == ret) 
    {  
        fprintf(stderr, "stat error\n");  
        return 1;  
    }  
  
    // 输出文件类型  
    if (S_ISREG(st.st_mode))    //如果 st_mode 的文件类型位与 S_ISREG 宏定义的掩码相匹配,则 
                                  S_ISREG(st.st_mode) 将返回非零值(通常为真),表示 
                                  该文件是一个普通文件。
    {  
        fputc('-', stdout);  
    } else if (S_ISDIR(st.st_mode))  
    {  
        fputc('d', stdout);  
    } else {  
        fputc('o', stdout); // 其他类型  
    }  
  
    // 输出文件权限  
    printf("%c%c%c",  
           (st.st_mode & S_IRUSR) ? 'r' : '-',  
           (st.st_mode & S_IWUSR) ? 'w' : '-',  
           (st.st_mode & S_IXUSR) ? 'x' : '-'  
    );  
  
    // 组权限  
    printf("%c%c%c",  
           (st.st_mode & S_IRGRP) ? 'r' : '-',  
           (st.st_mode & S_IWGRP) ? 'w' : '-',  
           (st.st_mode & S_IXGRP) ? 'x' : '-'  
    );  
  
    // 其他用户权限  
    printf("%c%c%c",  
           (st.st_mode & S_IROTH) ? 'r' : '-',  
           (st.st_mode & S_IWOTH) ? 'w' : '-',  
           (st.st_mode & S_IXOTH) ? 'x' : '-'  
    );  
  
    // 输出硬链接数、用户ID、组ID、文件大小、最后修改时间(秒数)和文件名  
    printf(" %lu %u %u %lu %lu %s\n",  
           st.st_nlink, st.st_uid, st.st_gid, st.st_size, (unsigned long)st.st_mtime, filename);  
  
    return 0;  
}

三、获取时间

1.获取秒数    
2.转换为需要个格式    

1.time

time_t time(time_t *t);

功能:获得1970年到现在的秒数
参数:t:存放秒数的空间首地址
返回值:
    成功返回1970年到现在的秒数
    失败返回-1
使用:先定义time_t tm;
方式1:time(&tm);方式2:tm = time(NULL);

2.ctime

char *ctime(const time_t *timep);//date
功能:将时间秒数转化成字符串
参数:timep:保存时间空间的地址
返回值:
    成功返回获得时间字符串的首地址
    失败返回NULL

3、localtime

struct tm *localtime(const time_t *timep);
功能:将一个秒数转化成日历时间
参数:timep:保存秒数空间的地址
返回值:
    成功返回保存日历时间结构体的指针
    失败返回NULL

struct tm 
 {
int tm_sec;         /* seconds */
int tm_min;         /* minutes */
int tm_hour;        /* hours */
int tm_mday;        /* day of the month */
int tm_mon;         /* month */
int tm_year;        /* year */
int tm_wday;        /* day of the week */
int tm_yday;        /* day in the year */
int tm_isdst;       /* daylight saving time */
};

练习:先用stat获取文件的秒数,再用localtime转换

#include
#include 
#include 
#include 
#include 
#include 
#include 
int main(int argc, const char *argv[])
{

	struct stat s;
	stat("./2.txt",&s);
	time_t tm;
	tm=s.st_mtime;
	//time(&tm);
	//printf("%s\n",ctime(&tm));
	struct tm *t=localtime(&tm);
	 printf("%d-%d-%d %d:%d:%d\n",t->tm_year+1900 ,t->tm_mon+1,t->tm_mday,t->tm_hour
           ,t->tm_min,t->tm_sec);
	
	return 0;
}

你可能感兴趣的:(c语言,开发语言,学习,linux)