• php基础-10


    PHP日期函数

    PHP date() 函数可把时间戳格式化为可读性更好的日期和时间。

    时间戳是一个字符序列,表示一定的事件发生的日期/时间。

    语法

    string date ( string $format [, int $timestamp ] )
    
    参数 描述
    format 必需。规定时间戳的格式。
    timestamp 可选。规定时间戳。默认是当前的日期和时间。

    date() 函数的第一个必需参数 format 规定了如何格式化日期/时间。

    这里列出了一些可用的字符:

    • d - 代表月中的天 (01 - 31)
    • m - 代表月 (01 - 12)
    • Y - 代表年 (四位数)

    如需了解 format 参数中可用的所有字符列表,请查阅我们的 PHP Date 参考手册,date() 函数

    可以在字母之间插入其他字符,比如 "/"、"." 或者 "-",这样就可以增加附加格式了:

    <?php
    echo date("Y/m/d") . "<br>";
    echo date("Y.m.d") . "<br>";
    echo date("Y-m-d");
    ?>
    >>>
    2016/10/21
    2016.10.21
    2016-10-21
    

    PHP 包含文件


    PHP include 和 require 语句

    在 PHP 中,您可以在服务器执行 PHP 文件之前在该文件中插入一个文件的内容。

    include 和 require 语句用于在执行流中插入写在其他文件中的有用的代码。

    include 和 require 除了处理错误的方式不同之外,在其他方面都是相同的:

    • require 生成一个致命错误(E_COMPILE_ERROR),在错误发生后脚本会停止执行。
    • include 生成一个警告(E_WARNING),在错误发生后脚本会继续执行。

    因此,如果您希望继续执行,并向用户输出结果,即使包含文件已丢失,那么请使用 include。否则,在框架、CMS 或者复杂的 PHP 应用程序编程中,请始终使用 require 向执行流引用关键文件。这有助于提高应用程序的安全性和完整性,在某个关键文件意外丢失的情况下。

    包含文件省去了大量的工作。这意味着您可以为所有网页创建标准页头、页脚或者菜单文件。然后,在页头需要更新时,您只需更新这个页头包含文件即可。

    include 'filename';
    或者
    require 'filename';
    

    1、假设您有一个标准的页头文件,名为 "header.php"。如需在同一个页面中引用这个页头文件,请使用 include/require:

    下面这个是.php文件

    <html>
    <head>
    <meta charset="utf-8">
    <title>菜鸟教程(runoob.com)</title>
    </head>
    <body>
    
    <?php include 'header.php'; ?>    <!--请使用 include/require-->
    <h1>欢迎来到我的主页!</h1>
    <p>一些文本。</p>
    
    </body>
    </html>
    

    输出结果:

    2、假设我们有一个在所有页面中使用的标准菜单文件。

    "menu.php":

    echo '<a href="/">主页</a>
    <a href="/html">HTML 教程</a>
    <a href="/php">PHP 教程</a>';
    

    网站中的所有页面均应引用该菜单文件。以下是具体的做法:

    下面这个是.php文件

    <html>
    <head>
    <meta charset="utf-8">
    <title>菜鸟教程(runoob.com)</title>
    </head>
    <body>
    
    <div class="leftmenu">
    <?php include 'menu.php'; ?>
    </div>
    <h1>欢迎来到我的主页!</h1>
    <p>一些文本。</p>
    
    </body>
    </html>
    

    PHP 文件处理

    fopen() 函数用于在 PHP 中打开文件。


    打开文件

    fopen() 函数用于在 PHP 中打开文件。

    此函数的第一个参数含有要打开的文件的名称,第二个参数规定了使用哪种模式来打开文件:

    <html>
    <body>
    <?php
    $file=fopen("welcome.txt","r");
    ?>
    </body>
    </html>
    

    文件可能通过下列模式来打开:

    模式 描述
    r 只读。在文件的开头开始。
    r+ 读/写。在文件的开头开始。
    w 只写。打开并清空文件的内容;如果文件不存在,则创建新文件。
    w+ 读/写。打开并清空文件的内容;如果文件不存在,则创建新文件。
    a 追加。打开并向文件末尾进行写操作,如果文件不存在,则创建新文件。
    a+ 读/追加。通过向文件末尾写内容,来保持文件内容。
    x 只写。创建新文件。如果文件已存在,则返回 FALSE 和一个错误。
    x+ 读/写。创建新文件。如果文件已存在,则返回 FALSE 和一个错误。

    注释:如果 fopen() 函数无法打开指定文件,则返回 0 (false)。

    实例

    如果 fopen() 函数不能打开指定的文件,下面的实例会生成一段消息:

    <html>
    <body>
    <?php
    $file=fopen("welcome.txt","r") or exit("Unable to open file!");
    ?>
    </body>
    </html>
    >>>Warning: fopen(welcome.txt): failed to open stream: No such file or directory in E:php_enviromentPHPTutorialWWW1.php on line 4
    Unable to open file!
    

    关闭文件

    fclose() 函数用于关闭打开的文件:

    <?php
    $file = fopen("test.txt","r");
    //执行一些代码
    fclose($file);
    ?>
    

    检测文件末尾(EOF)

    feof() 函数检测是否已到达文件末尾(EOF)。

    在循环遍历未知长度的数据时,feof() 函数很有用。

    注意:在 w 、a 和 x 模式下,您无法读取打开的文件!

    if (feof($file)) echo "文件结尾"; 、// 如果出错或者文件指针到了文件末尾(EOF)则返回 TRUE,否则返回 FALSE。
    

    逐行读取文件

    fgets() 函数用于从文件中逐行读取文件。

    注释:在调用该函数之后,文件指针会移动到下一行。

    实例

    下面的实例逐行读取文件,直到文件末尾为止:

    <?php
    $file = fopen("welcome.txt", "r") or exit("无法打开文件!");
    // 读取文件每一行,直到文件结尾
    while(!feof($file)) 
    {
      echo fgets($file). "<br>";
    }
    fclose($file); // 读取后必须关闭
    ?>
    

    welcome.txt

    fafeqafqaf
    dawdfafaff
    `1`2`21333
    fqafafqwfq
    

    输出:

    逐字符读取文件

    fgetc() 函数用于从文件中逐字符地读取文件。

    注释:在调用该函数之后,文件指针会移动到下一个字符。

    实例

    下面的实例逐字符地读取文件,直到文件末尾为止:

    <?php
    $file=fopen("welcome.txt","r") or exit("无法打开文件!");
    while (!feof($file))
    {
      echo fgetc($file);
    }
    fclose($file);
    ?>
    >>>
    fafeqafqaf dawdfafaff `1`2`21333 fqafafqwfq
    

    如果打开一个文件,文件名为中文,如果系统编程和当前文档编码不一致,会导致文件找不到无法打开,解决方法是用 iconv 函数编码转换成一致,如下:

    $fpath=iconv('UTF-8','GB2312',"题库.csv");
    $file=fopen($fpath,"r") or exit("无法打开文件!");
    //此处省略相关操作
    fclose($file);    
    

    用相对路径打不开子目录中的文件时,可用绝对路径打开,如下:

    $file=fopen(dirname(__FILE__).'\files\tk.csv',"r") or exit("无法打开文件!");   
    //此处省略相关操作
    fclose($file);
    

    文件上传

    开发中需要上传图片、音乐、视频等等,这种上传传递是二进制数据。

    客户端上传文件

    文件域

    <input type="file" name="image">
    

    表单的enctype属性

    ​ 默认情况下,表单传递是字符流,不能传递二进制流,通过设置表单的enctype属性传递复合数据。

    enctype属性的值有:

    1. multipart/form-data:复合的表单数据(字符串/字符,二进制都可以传),需要二进制数据时,比如文件内容,请使用 "multipart/form-data", 文件上传必须设置此值
    2. text/plain:用于向服务器传递无格式的文本数据,主要用户电子邮件
    3. application/x-www-form-urlencoded:【默认】,表示传递的是带格式的文本数据。
    4. from标签的 type="file" 属性规定了应该把输入作为文件来处理。举例来说,当在浏览器中预览时,会看到输入框旁边有一个浏览按钮。

    单词

    multipart:复合
    form-data:表单数组
    
    <!DOCTYPE html>
    <html lang="en">
    <head>
    	<meta charset="UTF-8">
    	<title>Document</title>
    </head>
    <body>
    <?php 
    if(!empty($_POST)){
    	echo "<pre>";
    	print_r($_FILES);
    }
    ?>
    <form method="post" action="" enctype="multipart/form-data">
    	<input type="file" name="face">
    	<input type="submit" name="button" value="上传">
    </form>
    </body>
    </html>
    

    服务器接受文件

    超全局变量$_FILES是一个二维数组,用来保存客户端上传到服务器的文件信息,第一个行参数是表单的 input 标签的name属性值, 列参数有5个如下:
    1、$_FILES[][‘name’]:上传的文件名
    2、$_FILES[][‘type]:上传的类型,这个类型是MIME类型(image/jpeg、image/gif、image/png)
    3、$_FILES[][‘size’]:文件的大小,以字节为单位
    4、$_FILES[][‘tmp_name’]:文件上传时的临时文件
    5、$_FILES[][‘error’]:错误编码(值有0、1、2、3、4、6、7)0表示正确

    $_FILES[][‘error’]详解:没有5

    错误描述
    0 正确
    1 文件大小超过了php.ini中允许的最大值 upload_max_filesize = 2M
    2 文件大小超过了表单允许的最大值
    3 只有部分文件上传
    4 没有文件上传
    6 找不到临时文件
    7 文件写入失败

    hidden属性值:隐藏作用。隐藏域,在页面上不显示,但是可以将参数传递给下一页,也可以被本页的javascript函数获取。

    隐含域主要用于提交表单的时候传递动态参数。

    注意:MAX_FILE_SIZE必须在文件域的上面。

    只要掌握的错误号:0和4

    将上传文件移动到指定位置

    函数:

    move_uploaded_file(临时地址,目标地址)
    

    代码

    <body>
    <?php
    if(!empty($_POST)) {
    	if($_FILES['face']['error']==0){  //上传正确
            //文件上传
    		move_uploaded_file($_FILES['face']['tmp_name'],'./'.$_FILES['face']['name']); // tmp_name临时文件的参数,上面讲了,第一个参数是name属性值,在第14行
            // 目标地址:'./'.$_FILES['face']['name'],'./'表示在当前目录下。即将临时文件上传至当前目录下 
    	}else{
    		echo '上传有误';
    		echo '错误码:'.$_FILES['face']['error'];
    	}
    }
    ?>
    <form method="post" action="" enctype='multipart/form-data'>
    	<input type="file" name="face">
    	<input type="submit" name="button" value="上传">
    </form>
    </body>
    

    小结:上传的同名的文件要给覆盖

    与文件上传有关的配置

    post_max_size = 8M:表单允许的最大值

    upload_max_filesize = 2M:允许上传的文件大小

    upload_tmp_dir =F:wamp mp:指定临时文件地址,如果不指定,操作系统会指定。自己可以修改指定

    file_uploads = On:是否允许文件上传

    max_file_uploads = 20:允许同时上传20个文件

    优化文件上传

    更改文件名

    方法一:通过时间戳做文件名

    UNIX 时间戳(timestamp)是 PHP 中关于时间日期一个很重要的概念,它表示从 1970年1月1日 00:00:00 到当前时间的秒数之和。

    PHP提供了内置函数 time() 来取得服务器当前时间的时间戳。

    例子:

    <?php
    echo time();
    ?>
    

    上面的例子运行后得到的是一串类似这样的数字:1279115455

    我们可以通过 date()等函数将它格式化为我们需要的时间日期格式。

    有效的时间戳典型范围是格林威治时间 1901年12月13日 20:45:54 到 2038年1月19日 03:14:07(此范围符合 32 位有符号整数的最小值和最大值)。不过从 5.1.0 起,已经克服了年的范围只能是 1901 到 2038 之间的问题。

    提示

    1. time() 得到的总是当前的时间戳,所以是不固定的值
    2. 如果时间戳为负数,则为从1970年1月1日 00:00:00往前推

    时间差

    时间戳虽然看起来好像不太直观,但我们在对时间做计算时却很方便。例如我们要计算时间差,或者对两个时间做比较等,直接比较数字即可而不必分别去考虑年月日时分秒的换算。而且在效率上时间戳作为整型数据也会快得多。

    要求用户在登陆网站一定时间后失效而需要重新登录的例子:

    <?php
    $expiration = $time()+2*3600;	//得到当前时间延迟2小时候的时间戳
    //失效验证代码略
    ?>
    

    那么只需要用户在活动期间将当前时间戳与 $expiration 进行比较,如果大于 $expiration 则要求用户重新登录。

    页面执行时间

    计算当前页面执行时间的例子:

    <?php
    //do something
    sleep(3);
    //do something
    $running_time = time() - $_SERVER['REQUEST_TIME'];
    echo '页面运行时间:',$running_time,' 秒';
    ?>
    

    执行例子输出如下:

    页面运行时间:3 秒
    

    $_SERVER[‘REQUEST_TIME’]是 PHP 内置的当前页面开始运行时的时间戳,在当前页面运行结束时将

    time() - $_SERVER[‘REQUEST_TIME’]得到的就是当前页面运行的时间(秒):

    由于该例子没有其他更多内容,因此是用 sleep(3) 函数让页面执行延迟 3 秒钟。


    //  更改文件名,用当前的时间加个位的随机数来作为文件名(有可能同一时间刚好有两个客户端通过时间戳命名上传文件,那两个文件名字相同会被覆盖)
    <?php
    $path='face.stu.jpg';
    //echo strrchr($path,'.');	//从最后一个点开始截取,一直截取到最后, 到这一步会输出:.jpg
    echo time().rand(100,999).strrchr($path,'.');   // 输出:1594613333385.jpg(刷新一次,时间变,数据变,名称就变了)
    

    方法二:通过uniqid()实现

    $path='face.stu.jpg';
    echo uniqid().strrchr($path,'.'),'<br>';   //uniqid()会输出唯一的ID
    echo uniqid('goods_').strrchr($path,'.'),'<br>';   //带有前缀
    echo uniqid('goods_',true).strrchr($path,'.'),'<br>';  //唯一ID+随机数
    

    验证文件格式

    方法一:判断文件的扩展名(不能识别文件伪装)

    操作思路:将文件的后缀和允许的后缀对比

    // strrchr():搜索 "Shanghai" 在字符串中的位置,并返回从该位置到字符串结尾的所有字符:
    <?php
    echo strrchr("I love Shanghai!","Shang");
    ?>
    >>>Shanghai!
    
    <body>
    <?php
    if(!empty($_POST)) {
    	$allow=array('.jpg','.png','.gif');	//允许的扩展名构成的数组
    	$ext=strrchr($_FILES['face']['name'],'.');  //获取上传文件的扩展名
    	if(in_array($ext,$allow)) // in_array(),返回值是bool值,字符串ext是否在数组allow中
    		echo '允许上传';
    	else
    		echo '文件不合法';
    }
    ?>
    <form method="post" action="" enctype='multipart/form-data'>
    	<input type="file" name="face">
    	<input type="submit" name="button" value="上传">
    </form>
    </body>
    

    注意:比较扩展名不能防止文件伪装。

    方法二:通过$_FIELS[]['type']类型(不能识别文件伪装)

    <body>
    <?php
    if(!empty($_POST)) {
    	$allow=array('image/jpeg','image/png','image/gif');	//允许的类别
    	$mime=$_FILES['face']['type'];  //获取上传文件的类型
    	if(in_array($mime,$allow))
    		echo '允许上传';
    	else
    		echo '文件不合法';
    }
    ?>
    <form method="post" action="" enctype='multipart/form-data'>
    	<input type="file" name="face">
    	<input type="submit" name="button" value="上传">
    </form>
    </body>
    

    注意:比较$_FIELS[]['type']不能防止文件伪装。

    方法三:php_fileinfo扩展(可以防止文件伪装)

    ​ 在php.ini中开启fileinfo扩展

    extension=php_fileinfo.dll
    

    注意:开启fileinfo扩展以后,就可以使用finfo_*的函数了

    <body>
    <?php
    if(!empty($_POST)) {
    	//第一步:创建finfo资源
    	$info=finfo_open(FILEINFO_MIME_TYPE);
    	//var_dump($info);		//resource(2) of type (file_info) 
    	//第二步:将finfo资源和上传的文件(临时文件)做比较
    	$mime=finfo_file($info,$_FILES['face']['tmp_name']);
    	//第三步,比较是否合法
    	$allow=array('image/jpeg','image/png','image/gif');	//允许的类别
    	echo in_array($mime,$allow)?'合法':'不合法';
    }
    ?>
    <form method="post" action="" enctype='multipart/form-data'>
    	<input type="file" name="face">
    	<input type="submit" name="button" value="上传">
    </form>
    </body>
    

    小结:验证文件格式有三种方法

    1、可以验证扩展名(不可以防止文件伪装)

    2、通过$_FILES[]['type']验证(不可以防止文件伪装)

    3、通过file_info扩展(可以防止文件伪装)

    优化文件上传例题

    步骤

    第一步:验证是否有误

    第二步:验证格式

    第三步:验证大小

    第四步:验证是否是http上传

    第五步:上传实现

    <body>
    <?php
    /**
    *验证错误
    *如果有错,就返回错误,如果没错,就返回null
    */
    function check($file) {
    	//1:验证是否有误
    	if($file['error']!=0){
    		switch($file['error']) {
    			case 1:
    				return '文件大小超过了php.ini中允许的最大值,最大值是:'.ini_get('upload_max_filesize');
    			case 2:
    				return '文件大小超过了表单允许的最大值';
    			case 3:
    				return '只有部分文件上传';
    			case 4:
    				return '没有文件上传';
    			case 6:
    				return '找不到临时文件';
    			case 7:
    				return '文件写入失败';
    			default:
    				return '未知错误';
    		}
    	}
    	//2、验证格式
    	$info=finfo_open(FILEINFO_MIME_TYPE);
    	$mime=finfo_file($info,$file['tmp_name']);
    	$allow=array('image/jpeg','image/png','image/gif');	//允许的类别
    	if(!in_array($mime,$allow)){
    		return '只能上传'.implode(',',$allow).'格式';
    	}
    	//3、验证大小
    	$size=123456789;
    	if($file['size']>$size){
    		return '文件大小不能超过'.number_format($size/1024,1).'K';
    	}
    	//4、验证是否是http上传
    	if(!is_uploaded_file($file['tmp_name']))
    		return '文件不是HTTP POST上传的<br>';
    	return null;  //没有错误
    }
    
    //表单提交
    if(!empty($_POST)) {
    	//上传文件过程中有错误就显示错误
    	if($error=check($_FILES['face'])){
    		echo $error;
    	}else{
    		//文件上传,上传的文件保存到当天的文件夹中
            // date('Y-m-d H:i:s', 1231346);将时间戳变格式,如果没有第二个参数,默认是将当前的时间戳改变格式
    		$foldername=date('Y-m-d H:i:s');		//文件夹名称,通过date()函数将当前的时间戳的格式变成年-月-日 小时:分钟:秒的形式
            // date('Y-m-d H:i:s')发现时间输出不对,需要修改当前版本的php的php.ini文件里的date.timezone = PRC(改成Peoples Republic China时区,默认不写是东一区即英国的格林尼治)
            // 成功显示2020-07-13 16:08:54
    		$folderpath="./uploads/{$foldername}";	//文件夹路径(事先在WWW文件夹下新建这个uploads文件夹)
    		if(!is_dir($folderpath))
    			mkdir($folderpath);
    		$filename=uniqid('',true).strrchr($_FILES['face']['name'],'.');	//文件名(用当前的时间戳来命名,以便清楚的知道所有文件的上传日期,便于区分,当有大量文件存在,可能夹杂着病毒文件)
    		$filepath="$folderpath/$filename";	//文件路径/文件名
    		if(move_uploaded_file($_FILES['face']['tmp_name'],$filepath)) // 文件移动函数:
    			echo "上传成功,路径是:{$foldername}/{$filename}";
    		else
    			echo '上传失败<br>';
    	}
    }
    ?>
    <form method="post" action="" enctype='multipart/form-data'>
    	<input type="file" name="face">
    	<input type="submit" name="button" value="上传">
    </form>
    </body>
    

    运行结果

    小结:

    1、将时间戳转换格式

    echo date('Y-m-d H:i:s',1231346),'<br>';		//将时间戳转成年-月-日 小时:分钟:秒
    echo date('Y-m-d H:i:s'),'<br>';	//将当前的时间转成年-月-日 小时:分钟:秒
    

    2、设置时区(php.ini)

    PRC:中华人民共和国
    

    3、PHP的执行可以不需要Apache的参与

  • 相关阅读:
    lora网关模块的原理
    Redis(三)Redis的高性能和持久化
    Redis(二)Redis基本数据结构和使用场景剖析
    Redis(一)安装redis【linux版】
    并发编程(九)抽象队列同步器AQS解析
    then、catch正常返回时Promise的状态,如何修改Promise的状态
    promise优化回调地狱
    es集群状态正常,kibana报500的server error的处理办法
    Node.js(一)Node.js简介、安装及环境配置之Windows篇
    JavaScript(一)JS的历史和简介
  • 原文地址:https://www.cnblogs.com/IronMind/p/13293988.html
Copyright © 2020-2023  润新知