linux下实现ls()函数遍历目录

需求:在linux下遍历目录,输出目录中各文件名。

  在linux下遍历目录的相关函数有:

  #include <dirent.h>

  DIR* opendir(const char* dir_path);

  struct dirent* readdir(DIR* dirp);

  int closedir(DIR* dirp);

  int lstat(const chat* filename,struct stat* st);

在这里涉及到几个结构体:DIR,struct dirent,struct stat:

  DIR结构体是一个内部结构,类似与FILE,用来保存当前被读取的目录的信息:

truct __dirstream
{
    void     *__fd;
    char     *__data;
    int        __entry_data;
    char     *__ptr;
    int       __entry_ptr;
    size_t  __allocation;
    size_t  __size;
    __libc_lock_define (, __lock)
}; 

typedef struct __dirstream DIR;

  struct dirent,指向文件夹下的目录内容:

struct dirent
{
long d_ino; /* inode number 索引节点号 */
off_t d_off; /* offset to this dirent 在目录文件中的偏移 */
unsigned short d_reclen; /* length of this d_name 文件名长 */
unsigned char d_type; /* the type of d_name 文件类型 */
char d_name [NAME_MAX+1]; /* file name (null-terminated) 文件名,最长256字符 */
}

  struct stat结构体保存文件信息,通过stat(),fstat(),lstat()函数返回,这三个函数的区别是:stat()传入文件路径得到stat,lstat()当传入的是符号链文件时,得到的是符号链文件的信息而不是符号链指向的文件,fstat()传入的是文件描述符而不是文件路径。

struct stat {
    dev_t     st_dev;     /* ID of device containing file */
    ino_t     st_ino;     /* inode number */
    mode_t    st_mode;    /* protection */
    nlink_t   st_nlink;   /* number of hard links */
    uid_t     st_uid;     /* user ID of owner */
    gid_t     st_gid;     /* group ID of owner */
    dev_t     st_rdev;    /* device ID (if special file) */
    off_t     st_size;    /* total size, in bytes */
    blksize_t st_blksize; /* blocksize for file system I/O */
    blkcnt_t  st_blocks;  /* number of 512B blocks allocated */
    time_t    st_atime;   /* time of last access */
    time_t    st_mtime;   /* time of last modification */
    time_t    st_ctime;   /* time of last status change */
};

  以下是ls()函数的全部实现,通过opendir()得到DIR*指针,readdir()函数获得指向struct dirent结构的指针,再通过struct stat得到每一个文件的信息。按字母顺序先输出目录文件名,再输出普通文件。

int ls(std::string path,std::string& ret)
{
    DIR* dirp = opendir(path.c_str());
    if(!dirp)
    {
        return -1;
    }
    struct stat st;
    struct dirent *dir;
    std::vector<std::string> file_name;
    std::vector<std::string> dir_name;
    while((dir = readdir(dirp)) != NULL)
    {
        if(strcmp(dir->d_name,".") == 0 ||
                   strcmp(dir->d_name,"..") == 0)
        {
            continue;
        }
        std::string full_path = path + dir->d_name;
        if(lstat(full_path.c_str(),&st) == -1)
        {
            continue;
        }
        std::string name = dir->d_name;

        //replace the blank char in name with "%$".
        while(name.find(" ") != std::string::npos)
        {
            name.replace(name.find(" "),1,"$%");
        }

        if(S_ISDIR(st.st_mode))   //S_ISDIR()宏判断是否是目录文件
        {
            name += "[d]";
            dir_name.push_back(name);
        }
        else
        {
            file_name.push_back(name);
        }
    }

    closedir(dirp);

    sort(file_name.begin(),file_name.end());
    sort(dir_name.begin(),dir_name.end());

    std::stringstream ss_ret;
    int count = 0;

    for(auto i=dir_name.begin();i!=dir_name.end();i++)
    {
        ss_ret<<*i;
        count++;
        if(count%5 == 0)
        {
            ss_ret<<std::endl;
        }
        else
        {
            ss_ret<<"  ";
        }
    }

    for(auto i=file_name.begin();i!=file_name.end();i++)
    {
        ss_ret<<*i;
        count++;
        if(count%5 == 0) //每五个名字回车。
        {
            ss_ret<<std::endl;
        }
        else
        {
            ss_ret<<"  ";
        }
    }

    ret = ss_ret.str();

    return 0;
}

  

时间: 2024-10-13 17:46:57

linux下实现ls()函数遍历目录的相关文章

编程实现Linux下的ls -l

头文件 #ifndef __FUNC_H__ #define __FUNC_H__ #include<stdio.h> #include <stdio.h> #include <stdio.h> #include <stdlib.h> #include <string.h> #include <sys/types.h> #include <dirent.h> #include <sys/stat.h> #inc

Linux 下的权限改变与目录配置

Linux 下的权限改变与目录配置 ./代表本目录的意思. (1):用户与用户组, 1:文件所有者,文件被某一用户所有 2:用户组:    对文件给与一个或者多个用户权限配置 3:其它人: (2):linux用户身份与用户组记录的文件 1:root 相关信息记录到 /etc/passwd中 2:个人密码记录到/etc/shadow中 3:linux所有的组名记录在/etc/group中 (3):linux文件权限概念 :permission deny,无权限的提示 (4):linux 的权限属性

在Linux下挂载Windows系统共享目录

在Linux下挂载Windows系统共享目录 默认情况下,Linux服务器会装有samba-client,但是没有装samba-server.但是访问Windows系统共享,安装有samba-client就可以了. [[email protected] ~]# rpm -qa | grep samba samba-3.6.23-14.el6_6.x86_64 samba-client-3.6.23-14.el6_6.x86_64 samba-common-3.6.23-14.el6_6.x86_

实现Linux下的ls -l命令

基本实现了Linux下的ls -l命令,对于不同的文件显示不同的颜色和显示符号链接暂时没有实现: 1 /************************************************************************* 2 > File Name: dirwalk.c 3 > Author: 4 > Mail: 5 > Created Time: Tue 31 Mar 2015 11:56:38 AM CST 6 ******************

Linux下如何修改用户默认目录

Linux下默认的用户目录一般为/home/xxx(root用户除外),有些时候我们可能需要修改这个目录,下面我就给大家分享2中修改的方法 工具/原料 Linux操作系统 方法/步骤 1 1.切换到root用户,直接修改/etc/passwd文件,找到你的用户名你一行,如下图所示修改路径,然后保存即可. 2 2.切换到root用户,使用usermod命令,例如usermod -d /tmp test (test为你的用户名),使用该命令请确保该用户下没有运行的软件或进程 3 最后切换到普通账户,

linux下转格式函数iconv段错误

今天将windows代码移植到Linux下,其中用到了Unicode转char的函数,被坑了一会,相关函数及编码格式,Linux与windows不同,有几点需要注意: 1.wchar_t 在Linux下占用4个字节,在windows下占2个字节: 2.Linux默认的文本编码方式是UTF-8:Linux终端汉字显示的设置方式:vi /etc/sysconfig/i18n: 设置LANG="en_US.UTF-8"或者LANG="zh_CN.UTF-8": 3.ico

linux下的信号处理函数总结

1.信号处理函数 相关函数原型如下: #include <signal.h> sighandler_t signal(int signum, sighandler_t handler); 第一参数是信号 第二个参数是信号处理器:             1.可以是SIG_DFL,信号的默认动作             2. 可以是SIG_IGN,忽略该信号             3. 一个带有一个整型参数的处理函数. #include <signal.h> int sigacti

Linux 下mysql修改数据库存放目录方法和可能遇到的问题

MySQL版本:5.6.23-enterprise-commercial-advanced ,使用rpm安装linux:Red Hat Enterprise Linux Server release 6.3 (Santiago)一 .如果是linux下用rpm包安装的mysql,修改方法如下: MySQL默认的数据文件存储目录为/var/lib/mysql.假如要把目录移到/home/data下需要进行下面几步: 1.home目录下建立data目录 cd /home mkdir data 2.把

linux下C语言函数执行时间统计

转载:http://blog.csdn.net/linquidx/article/details/5916701#t5 写好程序,用gcc编译,带上-pg参数,然后运行以后分析gmon.out文件: 命令exp:   gprof ./test-main ./gmon.out >1.log  在1.log中会生成各函数运行情况. gprof 1.1 简介 gprof实际上只是一个用于读取profile结果文件的工具.gprof采用混合方法来收集程序的统计信息,他使用检测方法,在编译过程中在函数入口