资源描述
///////////////////////// 第一天 系统调用 ---目录///////////////////////////////////////////////////////////////////////
一、设备及文件操作
linux操作系统把所有的设备都当作文件处理。linux文件类型常见的有普通文件、目录文件、设备文件、链接文件、管道文件。
ls -l
crw-rw-rw- 1 root root 1, 5 07-05 08:54 zero
文件类型:
- 普通文件
d 目录
l 链接
c 字符设备
b 块设备
p 先入先出设备(管道)
u 非缓冲设备
**其中,链接分为硬链接和符号链接。对文件硬链接后,只增加了文件的引用计数,并没有物理上增加文件。
符号链接是一个物理上真实存在的文件,该文件的内容是指向被链接文件的指针。
权限
rwx chmod 777 属主属组其它
文件引用计数
文件属主
文件属组
文件大小
文件修改日期
文件名
(一).目录操作
在linux中,目录是一种特殊文件,称为目录文件。
1.基本概念
工作目录:即进入系统后所在的当前目录,可以随时改变,用“.”表示,其父目录为“..”
用户目录:创建用户时创建的目录。每个用户都有自已的主目录。可以通过~引用自已的主目录。
路径:从树型目录的某个目录层次到某个文件的一条通路。各目录层次中间用/分隔
路径分为相对路径和绝对路径。
绝对路径:从根目录/开始,只有一条,是固定不变的。
相对路径:随工作目录的变化而不断变化。
2.目录操作的基本函数
头文件
#include <sys/types.h> 对外提供的各种数据类型 如 size_t
#include <sys/stat.h> 对外提供的各种结构类型 如 time_t
1)创建目录
int mkdir(const char *path,mode_t mode);
path: 要创建的目录文件名称,可为绝对路径或相对路径
mode: 新创建目录的权限。
S_IRUSR 属主读权限 4
S_IWUSR 属主写权限 2
S_IXUSR 属主执行权限 1
S_IRGRP 属组读权限
S_IUGRP 属组写权限
S_IXGRP 属组执行权限
S_IROTH 其它用户读权限
S_IUOTH 其它用户写权限
S_IXOTH 其它用户执行权限
使用时,可用或运算组合使用,如
S_IRUSR | SIWUSR
写可以使用数字,如
666
返回值:0 成功 -1失败。
说明:创建目录成功后,系统将在新目录下自动创建两个子目录“.”和“..”
2)删除目录
int rmdir(const char *path);
path:要删除的目录文件名称
返回值:0成功,-1失败
说明:只能用于删除空目录。
* 5)读取目录
#include <dirent.h> //目录文件函数头
打开目录
DIR *opendir(const char *pathname)
读取目录,返回一个指针,返回的结构保存目录中下一个目录项的相关数据。
struct dirent *readdir(DIR *dp)
将目录的读指针重新返回到第一个目录项
void rewinddir(DIR *dp)
关闭已打开的目录项
int colsedir(DIR *dp)
4)获取工作目录
char *getcwd(char *buf,size_t size);
buf:保存到工作目录名,称为缓存
size:缓存大小
返回值:调用成功,返回当前工作目录,否则返回NULL
pathname:目录名称
dp DIR结构指针,是目录文件结构定义
struct dirent{
ino_t d_ino; //目录文件的inode节点编号
off_t d_off; //目录文件开始至目录进入点的位移
unsigned short d_reclen; //d_name的长度,不包含NULL
unsigned char d_type; //d_name所指的文件类型
char d_name[256];//文件名或目录
};
* 6)获取文件或目录状态
#include <sys/stat.h>
int stat(const char *file,struct stat *buf)//未打开的文件
int fstat(int fd,struct stat* buf) //已打开的文件
file:文件名
fd:已打开的文件描述符
buf:指向stat结构的指针,用于保存获取的文件状态数据,结构如下:
struct stat{
unsigned long st_dev; //文件所在设备的标识
unsigned long st_ino; //文件结点号
unsigned short st_mode; //文件保护模式
unsigned short st_nlink; //硬链接数
unsigned short st_uid; //文件用户标识
unsigned short st_gid; //文件用户组标识
unsigned long st_rdev; //文件特殊设备标识
unsigned long st_size; //文件总大小,字节为单位
unsigned long st_blksize; //文件系统的块大小
unsigned long st_blocks; //文件分配给文件的块数量,512字节为单元
unsigned long st_atime; //文件最后访问时间
unsigned long st_atime_nsec;
unsigned long st_mtime; //文件最后修改时间
unsigned long st_mtime_nsec;
unsigned long st_ctime; //文件最后状态改变时间
unsigned long st_ctime_nsec;
};
例:获取文件大小
struct stat mystat;
fstat(fd,&mystat);
int size=mystat.st_size;//文件的大小
10)文件类型获取
S_ISREG() 判断是否为普通文件
S_ISDIR() 判断是否为目录文件
S_ISCHR() 判断是否为字符特殊文件
S_ISBLK() 判断是否为块特殊文件
S_ISFIFO() 判断是否为管道或FIFO文件
S_ISLNK() 判断是否为符号链接
S_ISSOCK() 判断是否为套接字
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/statfs.h>
例:
main(){
stat(pDirent->d_name,&fbuf); //读取目录项的信息
if(S_ISDIR(fbuf.st_mode) && memcmp(pDirent->d_name,".",1)!= 0
}
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/statfs.h>
main()
{
struct statfs buf;
struct stat fbuf;
memset(&fbuf,0x00,sizeof(fbuf));
stat("/etc/passwd",&fbuf);
printf("The size of file /etc/passwd is %ld bytes.\n", fbuf.st_size);
printf("The type of file /etc/passwd is ");
if(S_ISREG(fbuf.st_mode)) printf("regular file.\n");
else if(S_ISDIR(fbuf.st_mode)) printf("directory file.\n");
else if(S_ISCHR(fbuf.st_mode)) printf("character special file.\n");
else if(S_ISBLK(fbuf.st_mode)) printf("block special file.\n");
else if(S_ISFIFO(fbuf.st_mode)) printf("fifo file.\n");
else printf("other file.\n");
//write(STDERR_FILENO,szOutBuffer,strlen(szOutBuffer));
}
3.函数应用
#include <sys/types.h>
#include <unistd.h>
#include <dirent.h>
#include <sys/stat.h>
void SearchDir(char *szDir)
{
struct dirent *pDirent;
struct stat fbuf; //目录结构变量
char szOut[256];
DIR *dp = opendir(szDir); //打开目录
if (!dp)
{
return;
}
chdir(szDir); //改变工作目录到szDir
while (pDirent=readdir(dp))//循环读取目录szDir目录中的目录项
{
memset(&fbuf,0x00,sizeof(fbuf));
stat(pDirent->d_name,&fbuf); //读取目录项的信息
if(S_ISDIR(fbuf.st_mode) && memcmp(pDirent->d_name,".",1)!= 0
&& memcmp(pDirent->d_name,"..",2)!= 0) //判断是否是目录,并且不是.和..
{
memset(szOut,0x00,sizeof(szOut));
sprintf(szOut,"%s/%-s",szDir,pDirent->d_name); //读取目录名
write(STDOUT_FILENO,szOut,strlen(szOut));
write(STDOUT_FILENO,"\n",1);
SearchDir(szOut); //递归调用当前函数,遍历子目录
}
}
chdir(".."); //为关闭目录需要修改工作目录为非当前目录
closedir(dp); //关闭目录
return;
}
int main(int argc,char *argv[])
{
if (argc < 2) exit(1);
SearchDir(argv[1]);
return 0;
}
//---------------下午--------------------------------
(二).错误处理
1)读取错误号及错误信息
strerror(int errno);
处理
int err= bind(1,NULL,2);
if (err==-1){
printf("%s\n",strerror(errno));//用英文件打印原提示信息
if (errno==EPROTONOSUPPORT) printf("汉字\n"); //获取错误号后,打印相应的提示
}
2)检查条件是否成立
#include <assert.h>
void assert( int expression );
assert的作用是现计算表达式 expression ,如果其值为假(即为0),那么它先向stderr打印一条出错信息,然后通过调用 abort 来终止程序运行。
#include
#include
int main( void )
{
FILE *fp;
fp = fopen( "test.txt", "w" );//以可写方式打开一个文件,如果不存在就创建一个同名文件
assert( fp ); //所以这里不会出错
fclose( fp );
fp = fopen("noexitfile.txt", "r" );//以只读方式打开一个文件,如果不存在就打开文件失败
assert( fp ); //所以这里出错
fclose( fp ); //程序永远都执行不到这里来
return 0;
}
2.时间操作函数
sleep(int s); //秒
usleep(int us); //微秒
#include <time.h>
获取当前系统时间 UTC
time_t time(time_t* t);
获取北京时间
struct tm *locattime(time_t *timep);
timep:是time的返回值
返回值的结构:
struct tm{
int tm_sec; //秒
int tm_min; //分
int tm_hour; //时
int tm_mday; //日
int tm_mon; //月 从0算起
int tm_year; //年 从1900年算起的年 即1900年为0 01 为1
int tm_wday; //星期几
int tm_yday; //一年的第几天
};
time_t t;
time(&t); //获取系统时间
struct tm *p=localtime(&t);
printf("y=%d,m=%d,d=%d,w=%d\n",p->tm_year+1900,p->tm_mon+1,p->tm_mday,p->tm_wday);
展开阅读全文