当前位置: 首页 > 后端技术 > PHP

PHP中的文件系统函数(三)

时间:2023-03-29 23:21:19 PHP

终于来到了我们最关心的部分,就是f相关函数的操作。基本上大部分的文件操作都是按照今天学习的内容来的。话不多说,下面我们来一一学习。文件读取文件的读取其实很简单,fopen()打开句柄,fread()读取内容,fclose()关闭句柄,经过一套程序就完成了操作。$f=fopen('./test.txt','r+');while(!feof($f)){$contents=fread($f,4);echo$contents,PHP_EOL;}//Rain//is//fall//ing//all//arou//nd,//Itf//alls//on//...//...的fopen()函数的第二个参数是我们可以操作的权限。这个大家应该不陌生,w表示可写,r表示可读,r+表示以读写方式打开文件并将文件指针指向文件头,a表示追加和写入。模式说明'r'以只读模式打开,将文件指针指向文件头。'r+'以读写方式打开,并将文件指针指向文件头。'w'以写入方式打开,将文件指针设置为文件开头并将文件大小截断为零。如果该文件不存在,请尝试创建它。'w+'以读写方式打开,将文件指针设置为文件头并将文件大小截断为零。如果该文件不存在,请尝试创建它。'a'以写入方式打开,将文件指针设置为文件末尾。如果该文件不存在,请尝试创建它。'a+'以读写方式打开,并将文件指针指向文件末尾。如果该文件不存在,请尝试创建它。'x'创建并打开以进行写入,将文件指针设置为文件的开头。如果文件已经存在,则fopen()调用失败并返回FALSE和E_WARNING级别的错误消息。如果该文件不存在,请尝试创建它。这相当于为底层open(2)系统调用指定O_EXCLO_CREAT标志。'x+'已创建并打开以进行读写,否则表现与'x'相同。'c'只打开文件进行写入。如果该文件不存在,则创建它。如果它存在,它既不会被截断(与'w'相反)也不会导致对该函数的调用失败(与'x'一样)'c+'打开文件进行读写;否则它的行为与“c”中的相同。fread()函数的第二个参数是每次读取的字节数。可以看到在测试代码中,我们是以4字节为单位读取的,所以文件内容是以4个字符Section分隔的逐行输出的。feof()用于判断当前文件的光标指针是否已经移动到末尾。游标操作说完游标,我们再来看看游标相关的操作。while(!feof($f)){$contents=fread($f,1024);echo$contents,PHP_EOL;}//倒带($f);while(!feof($f)){$contents=fread($f,1024);echo$contents,PHP_EOL;}//四周都在下雨,//雨落在田野和树上,//雨落在雨伞上,//雨落在海上的船只上。使用顶部的代码读取一次内容后,光标已到达末尾。这时候再循环是读不到文件内容的。需要使用rewind()函数来重置光标。读取单个字符rewind($f);while(($c=fgetc($f))!==false){echo$c,PHP_EOL;}//R//a//i//n//i//s//f//a//...//...fgetc()函数用于读取单个字符。这个函数比较简单,但是需要注意的是,如果你用它来读中文,效果是不行的,因为一个汉字占2、3个字节,用这个函数读出来的内容会出现乱码,我们就后面有例子。读取一行while(($c=fgets($f))!==false){echo$c,PHP_EOL;}//四周都在下雨,//雨落在田野和树上,//雨落在这里的伞,//而在海上的船只上。fgets()函数用于逐行读取文件内容。这个函数也是一个常用的函数,大家都很熟悉了。读取csv文件//fgetcsv$f=fopen('./csv_test.csv','r');while(($c=fgetcsv($f))!==false){print_r($c);}//数组//(//[0]=>49//[1]=>20//[2]=>0//[3]=>42//[4]=>5/10/202012:32:18//)//数组//(//[0]=>50//[1]=>21//[2]=>0//[3]=>74//[4]=>5/10/202012:32:29//)//数组//(//[0]=>51//[1]=>22//[2]=>0//[3]=>35.8//[4]=>5/10/202012:32:38//)//...//...fclose($f);CSV是什么文件我就不多解释了,在笔者毕业的第一个项目中,有很多操作CSV文件的小函数。也可以说这个fgetcsv()函数是作者对文件操作的启蒙函数。它可以很方便的逐行读取CSV,解析成数组格式供我们操作。但一般情况下,如果内容是从Excel文件转换过来的,我们会排除标题行的第一行。当然,这是基于业务发展的实际情况。读取过滤器HTML//fgetss$f=fopen('./html_test.txt','r');while(($c=fgetss($f))!==false){echo$c,PHP_EOL;}//PHP弃用:函数fgetss()已弃用fclose($f);fgetss()函数可以在读取文件时过滤掉HTML代码,但该函数已被弃用。中文阅读问题对于中文阅读,我们主要关心的是汉字和英文字符占用的字节数的区别。上面说了,如果中文是UTF8编码格式,会占用3个字节,如果是GBK之类的,会占用2个字节。所以如果我们使用fread(),我们需要使用相应编码的倍数来读取。比如我们下面的测试文件是UTF8编码的,需要读取三个字符,所以需要传参为6。//中文测试$f=fopen('./cn_test.txt','r+');while(!feof($f)){$contents=fread($f,6);echo$contents,PHP_EOL;}//MyBen//Inaction//野客//,Gone//Wandering//Tracingpeople//之间。//一次//正在读取//...//...while(!feof($f)){$contents=fread($f,1024);echo$contents,PHP_EOL;}//倒带($f);while(!feof($f)){$contents=fread($f,1024);echo$contents,PHP_EOL;}//我是一个流浪者,浪迹天涯。//一时被命名为名山。不可避免的即兴创作。//看破尘埃烦恼,何来闲暇。//柳霞认真吟诗。并与白云作伴。rewind($f);while(($c=fgetc($f))!==false){echo$c,PHP_EOL;}//?//?//?//......//......rewind($f);while(($c=fgets($f))!==false){echo$c,PHP_EOL;}//我是一个流浪者,浪迹天涯。//一时被命名为名山。不可避免的即兴创作。//看破尘埃烦恼,何来闲暇。//柳霞认真吟诗。并与白云作伴。fclose($f);fread()函数读取的内容为什么会出现乱码?因为我们的换行符按照英文代码还是只占一个字节!另外fgetc()函数惨了,fgets()函数还能正常读取。阅读其余内容$f=fopen('./cn_test.txt','r+');echofgets($f),PHP_EOL;//我是一个流浪者,浪迹天涯。echofpassthru($f),PHP_EOL;//一时被命名为名山。不可避免的即兴创作。//看破尘埃烦恼,何来闲暇。//柳霞认真吟诗。并与白云作伴。倒带($f);在这段测试代码中,我们使用fgets()读取一行内容,然后使用fpassthru()直接读取文件中剩余的所有内容。这就是fpassthru()函数的作用,它可以读取文件中光标之后的所有剩余内容。fseek($f,3*14+1);echofgets($f),PHP_EOL;//一时名山。不可避免的即兴创作。还有一个fseek()函数,可以指定从当前位置开始读取,也可以看成是游标操作的一部分。倒带($f);fseek($f,14*2*3+1);echoftell($f),PHP_EOL;//85ftell()函数返回文件的剩余字节信息。文件句柄信息print_r(fstat($f));//数组//(//[0]=>16777220//[1]=>8708492112//[2]=>33188//[3]=>1//[4]=>501//[5]=>20//[6]=>0//[7]=>177//[8]=>1603414680//[9]=>1603414679//[10]=>1603414679//[11]=>4096//[12]=>8//[dev]=>16777220//[ino]=>8708492112//[mode]=>33188//[nlink]=>1//[uid]=>501//[gid]=>20//[rdev]=>0//[size]=>177//[atime]=>1603414680//[mtime]=>1603414679//[ctime]=>1603414679//[blksize]=>4096//[blocks]=>8//)fstat()函数与我们上篇文章中提到的stat()函数相同,但是它需要的是一个句柄参数,然后返回句柄对应的文件的信息。而stat()直接给出文件的路径。文件截断//文件会变成ftruncate($f,14*2*3+4);echofread($f,8094),PHP_EOL;//我不是野客,浪迹天涯。//一时被命名为名山。不可避免的即兴创作。fclose($f);ftruncate()函数将从指定位置截断文件内容。这里我们只保留前两行的内容,后面的内容被截断了。请注意,使用此功能会更改原始文件的内容。从格式$f=fopen("users_test.txt","r")读取文件和输入;while($userinfo=fscanf($f,"%s\t%s\t%s\n")){print_r($userinfo);}//数组//(//[0]=>javier//[1]=>argonaut//[2]=>pe//)//Array//(//[0]=>hiroshi//[1]=>sculptor//[2]=>jp//)//Array//(//[0]=>robert//[1]=>slacker//[2]=>us//)//Array//(//[0]=>luigi//[1]=>florist//[2]=>it//)fclose($f);fscanf()函数文件的内容会根据第二个参数传入的内容进行格式化。就像使用printf()函数一样,只不过它是从读取的角度获取数据内容。这里使用制表符作为分隔符来形成格式化的结果数组。文件内容匹配var_dump(fnmatch('*fall[ing]*',file_get_contents('./test.txt')));//bool(true)fnmatch()函数用于判断给定的内容是否包含第一个参数中指定的规则。有点像正则表达式相关函数的用法,而且不是用来操作文件的,而是用来操作字符串的。但是它的规则定义是基于Linux系统中的文件操作匹配规则,也就是说它不是一个完整的正则规则。就像我们在Linux中经常查看一个文件的信息:ll*.txt。进程文件读取操作是什么意思?实际上,我们可以执行一段操作系统进程代码,然后得到它的结果。这个流会以文件流的形式返回给PHP,形成一个文件流句柄。$handle=popen("/bin/ls","r");while(!feof($handle)){echofgets($handle);}pclose($handle);//1.PHP函数中的日期相关(3).php//2.学习PHP.php中的目录操作//3.学习PHP.php中高精度定时器HRTime扩展//4.PHP.php中DirectIO直接操作文件扩展的使用//5.学习PHP.php中Fileinfo扩展的使用//6.PHP中的文件系统函数(1).php//7.PHP中的文件系统函数(2).php//8.PHP中的文件系统函数(3).php//cn_test.txt//csv_test.csv//html_test.txt//test.txt//timg.jpeg//users_test.txt//write.txt文件写入比较简单,就这么一点代码介绍。而且只有三个功能。//write$f=fopen('write.txt','w');fwrite($f,"ThisisTest!\n");fputs($f,"ThisisTest2!!\n");$csv=[['id','name'],[1,'Zyblog'],[2,'铁杆项目经理']];foreach($csvas$v){fputcsv($f,$v);}fclose($f);//ThisisTest!//ThisisTest2!!//id,name//1、Zyblog//2、硬核项目管理器fwrite()用于写入文件句柄Write内容。fputs()是fwrite()的别名,两者是一回事。fputcsv()函数将数组的内容以CSV格式写入文件。它还具有其他参数来修改用于分隔符的符号。这里我们默认为逗号。文件锁$fp=fopen("/tmp/lock.txt","w+");if(flock($fp,LOCK_EX)){//独占锁fwrite($fp,"Writedata:".date('H:i:s')."\n");如果(!$argv[1]){睡眠(50);}fflush($fp);//在释放锁之前刷新缓冲区flock($fp,LOCK_UN);//释放锁}else{echo"无法获取锁,无法写入!";}fclose($fp);锁定一个文件,然后其他操作就无法读取它,这种操作一般在多个线程或者多个函数同时对一个文件进行操作时是很常见的。flock()的第二个参数可以设置读锁、写锁等,这里我们使用的是LOCK_EX共享排他锁,也就是写锁。当我们运行这段代码时,其他脚本在停留时间内不能写入数据。如果有脚本同时操作这个文件,就会卡在这里,直到这里的锁被释放。LOCK_SH获取共享锁(读程序)。LOCK_EX获取独占锁(写入它的程序。LOCK_UN释放锁(无论是共享锁还是独占锁)。LOCK_NB如果您不希望flock()在锁定时阻塞(Windows尚不支持)。使用fflush()flushbuffer,这也是我之前提到的PHP中buffer相关的知识,大家可以回去复习一下PHP中outputbuffer的控制,在文件操作中,使用这个函数可以立即刷新buffer的内容,将内容写入到具体的文件中。总结的很搞笑吗?一下子学会了这么多函数。本文结束意味着PHP原生的文件操作函数已经学会了。当然,理解只是一方面,还有更多需要的,尝试应用到自己的项目中,测试代码:https://github.com/zhangyue0503/dev-blog/blob/master/php/202010/source/8.PHP中的文件系统函数(3).php参考文件:https://www.php.net/manual/zh/ref.filesystem.php各媒体平台可搜索【硬核项目经理】