时间:2023-05-27 03:09:01 | 来源:网站运营
时间:2023-05-27 03:09:01 来源:网站运营
小白7天入门PHP Web开发 - Day 4 后端PHP入门:《小白7天入门PHP Web开发》系列文章,面向单纯善良的完全不懂Web开发编程的入门速成课程,小白们如果感兴趣可以研读此系列文章,也可以连线提问。各路大神有何指教还请指点一二。希望各路大神手下留情,注意维护自己的身份和形象。拜谢各位。上一篇文章 我们学会了使用简单的CSS完成了对HTML页面的修饰和美化布局,以及以表单提交验证为例的JS的基本使用,这节我们开始尝试使用PHP来做后端处理表单提交后的相关操作。
PHP全称为 PHP: Hypertext Preprocessor(更名前是 Personal Home Page ),中文名字叫超文本预处理器,是一种开源脚本编程语言,是常用的web开发语言(从旧名称就可以看出)。这里我们需要了解一个概念:静态网站和动态网站。
<?php/* * PHP代码通常被包含在这个标签中 * 开始标签是 <?php * 结束标签是 ?> * 如果文件中只有PHP代码,没有任何别的东西,结束标签可以不要,这种情况下也建议 * 不要(避免页面输出一些空串影响页面) */// PHP 代码写在这里,如下面 echo "Hello PHP, hello web"; // 在页面上输出字符串 Hello PHP, hello web?>
2、运行环境<!-- score.html --><!-- 使用 localhost/score.html 访问或直接用浏览器打开文件 --><!-- score.html文件应与后续.php文件在同一个目录下 --><!DOCTYPE html><html><head> <meta charset="utf-8"> <meta http-equiv="X-UA-Compatible" content="IE=edge"> <title>成绩转评级</title> <style type="text/css"> /*通用样式*/ * { font-size: 14px; margin: 0; padding: 0; } /*说明部分样式*/ .explain { background-color: #f4f4f4; margin-top: 100px; padding: 20px 0px; } .block { text-align: left; width: 400px; margin: 0 auto; } .block ul { list-style: none; } /*表单部分样式*/ .form { width: 400px; margin: 0 auto; margin-top: 20px; } .form input, .form button { height: 36px; box-sizing: border-box; margin-top: 10px; padding: 5px 10px; } .form input { width: 100%; } .form button { width: 100px; } </style></head><body> <div class="explain"> <div class="block"> <ul> <li>1、 学生成绩90分(含)以上,评级为A</li> <li>2、 学生成绩在80分(含)以上,90分以下,评级为B</li> <li>3、 学生成绩在60分(含)以上,80分以下,评级为C</li> <li>4、 学生成绩在60分以下,评级为D</li> </ul> </div> </div> <div class="form"> <form action="scorelevel.php" method="get" accept-charset="utf-8" target="_blank" onsubmit="return checkform()"> <input type="text" name="study_name" value="" placeholder="请输入学生姓名"> <input type="text" name="study_score" value="" placeholder="请输入学生成绩"> <br> <button type="submit">检测评级</button> </form> </div> <script> function checkform() { var study_name = document.getElementsByName('study_name')[0].value; var study_score = document.getElementsByName('study_score')[0].value; if ( !(study_name && study_score) ) { alert('学生姓名和学生成绩不能为空'); return false; } } </script></body></html>
这个HTML文件叫 score.html,里面主要是一个表单与后端php文件交互,所以我们要新建一个在action属性里面的那个名字的php文件<form action="scorelevel.php" method="get" accept-charset="utf-8" _blank="self">
用sbt新建 scorelevel.php,注意这里建议 保持score.html和scorelevel.php同在根目录下(action里面其实就是php文件的地址,所以你能保证路径对就可以),以下是php文件的代码,你大可以先复制进去我们再来逐个了解。<?php/** * 我们以 “用户输入学生成绩,根据学生成绩对学生评级并输出” 的功能需求来做示例 * 需求的基本内容: * 学生成绩90分(含)以上,评级为A * 学生成绩在80分(含)以上,90分以下,评级为B * 学生成绩在60分(含)以上,80分以下,评级为C * 学生成绩在60分以下,评级为D */// 首先考虑,成绩从哪里来?用户输入提交过来的# 获取用户提交的学生名字和成绩$study_name = isset($_GET['study_name']) ? $_GET['study_name'] : '';$study_score = isset($_GET['study_score']) ? $_GET['study_score'] : '';// 初始化评级$level = '未知';$level_label = '未知';// 检测姓名和分数是否为空if ( $study_name == '' || $study_score == '' ) { echo '学生姓名和学生成绩未知,请检查提交的数据是否为空'; die;}// 根据分数给学生评级if ( $study_score >= 90 ) { $level = 'A';} elseif ( $study_score >= 80 && $study_score < 90 ) { $level = 'B';} elseif ( $study_score >= 60 && $study_score < 80 ) { $level = 'C';} elseif ( $study_score < 60 ) { $level = 'D';} else { $level = '未知';}switch ( $level ) { case 'A': $level_label = '优秀'; break; case 'B': $level_label = '良好'; break; case 'C': $level_label = '及格'; break; case 'D': $level_label = '差'; break;}echo '学生 '.$study_name.' 的成绩为 '. $study_score .',评级为:'.$level.'('. $level_label .')';die;
现在你在HTML页面上输入姓名和成绩,点击按钮“检测评级”,会打开一个新的页面,这个页面就是php文件的页面,但是他是处理过我们提交的数据最后输出内容到页面上来的。// 获取用户提交的学生名字和成绩$study_name = isset($_GET['study_name']) ? $_GET['study_name'] : '';$study_score = isset($_GET['study_score']) ? $_GET['study_score'] : '';// 初始化评级$level = '未知';
php中声明和定义变量使用 $ 美元符号,后面紧跟着变量名称,例如上面的 $study_name,$ 是php中声明和定义变量的语法,study_name 是变量名,代码通过变量名和计算机内存地址相对应进行存储和获取变量值。同时变量有不同类型(描述的变量值的类型),比如常见的:字符类型:可以理解为字符或字符串,如 $var = 'string';整型:可以理解为整数,包括正负数和0,都是整型,如 $var = 1; $var = -2;浮点型:可以理解为有小数的数字类型,如 $var = 1.12;布尔类型:可以理解为只有真、假两个值,如 $var = true; $var = false;数组:是一种数据结构,用于存储多个不同的值,如 $var = array('我是值1', '我是值2', 5);对象:是一种数据结构,是类的实例,对象存储了很多值,包括属性变量、方法等(后面我们会专门讲面向对象的时候讲到对象)
3.3 比较运算和数学运算:第三点,因为我们需要通过不同的分数不同的条件来换算出评级,所以要进行判断和比较,比较运算,顾名思义,就是要对多个值或变量进行比较,必出大小、是否相等、是否不相等等,比较运算的结果是布尔值,如$study_name == '' || $study_score == ''
其中符号 || 是或者的意思,只要满足其中任何一个条件就可以继续,符号在回车键上方,这个语句的意思就是:如果变量$study_name为空字符串或变量$study_score为空字符串的话就是真的;如果要两个或多个条件同时满足时用 && 符号连接。加法运算:$a = 1 + 1; // 结果是 $a = 2减法运算:$b = $a - 1; // 结果是 $b = 1乘法运算:$c = $a * $b; // 结果是 $c = 2除法运算:$d = 5 / $c; // 结果是 $d = 2.5取余/取模:$e = 5 % $c; // 结果是 $e = 1,就是余数,如果除数是负数,余数也是负数
3.4 分支语法,条件判断 if...elseif...else...if ( $study_score >= 90 ) { $level = 'A';} elseif ( $study_score >= 80 && $study_score < 90 ) { $level = 'B';} elseif ( $study_score >= 60 && $study_score < 80 ) { $level = 'C';} elseif ( $study_score < 60 ) { $level = 'D';} else { $level = '未知';}
if...elseif...else...主要用于处理不同条件下,处理的方式或者变量的值不一样的情况,就像找女朋友一样,列了一堆条件,挨个去筛选,直到符合条件时就交往,不符合继续找。主要结构如上。条件明确时,使用if或elseif+圆括号,括号里面是条件,即比较运算,当结果是真(true)时就执行对应花括号里面的代码。比如if ( 女孩身高 > 170 ) { echo "我要和她交往";} else { echo "孤独终老";}
如果女孩的身高大于170cm,那就交往,否则拒绝交往(你可能要孤独终老了)。当只有一个明确条件,其他都不清楚的时候,中间是可以没有elseif的,直接if...else...即可。switch ( $level ) { case 'A': $level_label = '优秀'; break; case 'B': $level_label = '良好'; break; case 'C': $level_label = '及格'; break; case 'D': $level_label = '差'; break;}
switch常用于有多个分支并且有确定值分类比较简单值的时候,上述代码时我们要对评级分别给予描述。基本语法结构如上,下面也再做个解释switch ( $level ) { // 分支关键字 switch 必须的,加圆括号和花括号,圆括号里面是变量或者一个有明确计算结果的表达式 case 'A': // 每一个分支都用 case 值:来开始 /*这里写代码和业务逻辑*/ break; // 每一个分支处理完代码业务逻辑,要跳出当前分支 case 'B': $level_label = '良好'; break; case 'C': $level_label = '及格'; break; case 'D': $level_label = '差'; break;}
switch和if...else...在很多情况下是可以互相替代的,并且可以随便嵌套,就是你中有我我中有你的这种感觉,因为switch和if...else..本身也是组成代码业务逻辑的一部分,当然可以放在彼此怀(dai)里(ma)了(li)echo '学生 '.$study_name.' 的成绩为 '. $study_score .',评级为:'.$level.'('. $level_label .')';die;
这里的代码中我们使用了 echo 这个关键字(php语法,php中预留了一些自用的单词),echo后面可以输出非数据结构类型的其他类型变量或值,比如,字符、数字(整型和浮点型)、布尔值等。而要输出打印数组(array)、对象(object)则需要用到以下两个函数print_r($array); // 通常用于数组打印var_dump($object); // 可以输出打印所有类型,会有类型提示灯详细信息print 'char'; // 与echo类似
常用的基本上就是我们以上者四种了,可以用来输出内容数据给用户看,也可以用来进行简单的代码调试(作用很大)。// php中数组的定义如下// 使用array()来定义数组,数组的值也可以是数组// 有键名(如下面的name和score用来描述后面的值是什么样的值)和值对的// 也有没有键名只有值得,下面的值array('name' => '章五二', 'score' => 85)就是没有键名的// 键名和值用符号 => 连接,数组里的每一个项(值)后面用逗号(,)结束,最后一项可以不用// 数组只有一层(如 array(1,2,3))叫一维数组,有两层(如下面的)叫二维数组,以此类推$score_arr = array( array('name' => '章五二', 'score' => 85), array('name' => '李小狗', 'score' => 65), array('name' => '孙儿了', 'score' => 99), array('name' => '韦小宝', 'score' => 59), array('name' => '任之初', 'score' => 88));// 或用短数组的方式来定义,就是中括号 [] 代替 array(),在php5.4以上的版本支持了,如下$score_arr = [ ['name' => '章五二', 'score' => 85]];
那怎么获取数组值呢?// 使用中括号和下标来获取,如[下标],包括数字索引和键名索引两种方式,键名存在的时候才可以使用键名// 例如,我要获取章五二的成绩就需要获取数组$score_arr的第一个值// (数组的索引下标从0开始,第一个值下标是0,第二个是1,以此类推)$score_arr[0]; // 这里获取到的是第一个值,array('name' => '章五二', 'score' => 85)// 然后在获取第一个值(也是数组)的score对应的分数值$score_arr[0]['score']; // 这里获取的是第一个值的分数,你可以使用echo或者其他输出方式,把她打印出来看看
现在数组有了,我们要进行批量处理的时候,就可以采用循环的方式,数组循环我们通常用 foreach ( $score_arr as $key => $value ) { // 获取每个人的成绩并输出 // 此时的 $value 就是数组的每一个值,从0(第一个)开始 // 如array('name' => '章五二', 'score' => 85) echo '学生 '. $value['name'] .' 的成绩为 '. $value['score'] . '<br>';}// 不断重复循环的去获取成绩,输出结果如下:/* 学生 章五二 的成绩为 85 学生 李小狗 的成绩为 65 学生 孙儿了 的成绩为 99 学生 韦小宝 的成绩为 59 学生 任之初 的成绩为 88*/
还有两个常用循环结构for(初始值; 条件判断表达式; 改变条件) { // 代码逻辑 }// 和初始值while(条件判断表达式) { // 代码逻辑 改变条件}
注意有三要素:初始值、条件判断、改变条件,同时注意for里面用的是分号而不是逗号。具体写法如下// 以从1加到100为例,你想说首尾相加乘以50就好了,还要什么代码执行,哦豁,那么我们就用乘的吧// 从1乘到100,hiahiahia// $i不断的变化,带来了循环和循环结束的可能性,每一轮循环,$i的值都在变化$total = 1; // 定义变量存储最终结果for ($i=1; $i <= 100; $i++) { $total = $total * $i; // 当对变量自身进行数学运算时可以简写,如 $total *= $i;}// 或用 while$total = 1;$i = 1;while ($i <= 100) { $total *= $i; $i++;}// 补充说明: $i++是自增1,同理$i--是自减1,同时符号放在前面也是可以的,结果一样,如++$i、--$i// 但他们有所区别,你可以简单理解为,符号在前面的,是先运算再使用,在后面的是先使用再运算,比如$i = 1;$val = $i++; // $val = 1, $i = 2$i = 1;$val = ++$i; // $val = 2, $i =2// 好好体会一下
至此,你需要了解的PHP入门的基本语法就差不多了,你可以自己尝试谢谢别的东西,比如模拟和用户的对话,用户选择问题提问,你针对问题返回输出不同的答案给用户等等。Just try it~!恭喜你,真的入门了。如果你还不满足,那么请接着往下看,以后我们都尽量用下面的知识来写php代码哦。PHP 的真正威力源自于它的函数。在 PHP 中,提供了超过 1000 个内建的函数。是不是听起来就有点炸。那么什么时候使用函数呢?一般要进行重复使用同样或类似的代码的时候就需要用到函数,函数来封装这部分代码,放在一处,处处可用,业务代码更简洁了,还能少些代码,同时功能解构了,互不影响,多好,何乐而不为。
函数名(参数)
函数名和变量名的命名规则一致,那参数是什么呢?var_dump('我就是参数,值');
非常简单的去理解的话,参数就是函数调用的时候括号里面的东东,比如上面的 '我就是参数,值',这整个就是参数。参数的作用就是将函数外部的变量、值等传递到函数内部使用,参数也分实参和形参,作为入门理解,我们简单的理解为,实参是外部传递到函数内部的时候的参数,形参则是函数定义的时候,定义的参数列表。// 假装我是源码里面的函数声明function var_dump($input) { // 这里是代码逻辑实现 }// 这里声明了函数var_dump,括号里面的就是形参了,$input// 我们调用var_dump$input = 'i am the input string';var_dump($input);// 这里调用时候传入的参数$input就可以理解为实参
由于php内置了很多函数,可以非常方便的使用,我们这里不详细列举,大家可以自己去了解下,后面我们用到的都会做对应讲解。function 函数名(参数1, 参数2, ...参数n) { 业务逻辑代码}
函数定义五要素:关键字function、函数名、圆括号和参数、花括号、花括号内的业务逻辑代码。// 第一个需求$total_1 = 1;$i_1 = 1;while ($i_1 <= 100) { $total_1 *= $i_1; $i_1++;}// 第二个需求$total_2 = 2;$i_2 = 2;while ($i_2 <= 100) { $total_2 *= $i_2; $i_2 += 2;}
然后,需求又变了,增加一个从10开始累乘每次自增10的值,不仅如此,还要把原来的从1开始的改成从5开始,(不要以为这样的需求不会出现,你以后干这一行你就会发现,无处不在,产品的思维不是你我能够理解的)如果按上面的写法,要继续加代码,并且很明显的发现,几个需求的代码几乎是一样的,只有两个东西不一样,这就很尴尬了,不断写差不多的东西,修改的时候还得修改很多地方,比如从1开始改成从5开始累乘3,你需要修改的地方有哪些,你自己数数。// 按函数声明的格式,我们写来个框架function multiply() {}
然后我们观察需求发现,经常变动的有两个东西,一个是起始值,一个是自增值,那么这种变动的东西,我们可以让她以后作为参数传到函数里面去。// 添加形参// $multiplicand 被乘数(起始值)// $increment 自增值function multiply($multiplicand, $increment) {}
然后就是把代码逻辑放到函数体(花括号内部分)内,使用参数来处理计算结果function multiply($multiplicand, $increment) { $total = $multiplicand; $i = $increment; while ($i <= 100) { $total *= $i; $i += $increment; }}
然后我们把结果从函数里面返回到函数外面,用 return 即可。function multiply($multiplicand, $increment) { $total = $multiplicand; $i = $increment; while ($i <= 100) { $total *= $i; $i += $increment; } return $total;}
这样我们上面的代码就可以变成/*function.php 专门放function函数的地方,也可以和业务代码放在一起*/function multiply($multiplicand, $increment) { $total = $multiplicand; $i = $increment; while ($i <= 100) { $total *= $i; $i += $increment; } return $total;}/*code.php*/// 使用 require 来包含其他 php 代码require 'function.php';echo multiply(1,1);echo multiply(2,2);
是不是看出来,在具体业务代码的code.php中,代码更简洁了,而且封装的函数multiply可以复用了。多好,多美好~!这里因为例子规模较小,优势可能你觉得没那么明显,慢慢等你长(shen)大(ru)了会知道的,不着急,一个阶段做一个事情嘛。在学校里,学生、老师是两群不同的群体,简单说就是两类人,这个时候,学生是一类,老师是一类,这就是类此时此刻的你,我觉得应该对类和对象以及对象的属性、方法有了一定的了解了。还记得上面你想到的把不同方法归类到不同文件吗?这个时候,我们可以把一个类写到一个文件,然后类里面有不同的方法,这样只要类名不同,我们的方法同名也不要紧,因为我们使用类的对象去调用的方法,每一个对象实例那都是不是同一个的。
在学生或老师的某一类里,每一个学生或老师,都是各自群体里的某一个个例,或者叫实际的例子,简称实例(话糙理不糙),比如张五、孙三,都是不一样的个体实例,我们就这叫实例化的对象,也就是类(学生群体)的对象(个体实例)
想想看,张五、孙三这两都有些什么共同的静态的东西,就是你有我也有的那种?想到了吗?没想到?不会吧~!身高?体重?是不是?腰围、胸围、臀围是不是?当然都是啊~!我们把这些称为对象的属性
张五、孙三除了有共同的静态的特征,还有一些共同的动态的东西,比如吃,比如喝,还有拉撒等,这些我们都可以称为对象的方法
<?php/** * Student.php * 这是一个学生类,类名 Student和文件名Student一致 * 方便读懂和找类的时候更容易找到和区分 *//** * 类声明的基本形式如下 * class 类名 {} */class Student {}
学生这一类人有哪些属性(特征)和方法(动作、能力)呢?<?php/** * Student.php * 这是一个学生类,类名 Student和文件名Student一致 * 方便读懂和找类的时候更容易找到和区分 *//** * 类声明的基本形式如下 * class 类名 {} */class Student { // 身高 public $height; // 体重 public $weight; /** * 吃 */ public function eat() { echo 'I am eatting~!'; } /** * 喝 */ public function drink() { echo 'Drinking too much~!'; }}
就这样,我们写了一个拥有两个方法(类里面的函数我们通常称为方法)和两个属性的学生类。有没有发现,类方法的声明和函数的几乎是一致的,而类属性和变量的声明也几乎是一样的。区别在哪里呢?你们都是明眼人,一看就知道多了个 public,这个关键字,和protected、private,并称类属性或方法的访问类型,也就简单的描述了属性和方法的访问限制<?php/** * class.php */// 包含类文件,也就包含了类require 'Student.php';// 实例化类,使用 new 类名() 的方式// 这样就得到了一个学生类Student的对象 $student$student = new Student();// 使用对象->的方式访问类的属性和方法var_dump($student->height);$student->eat();
既然讲到继承了,我们就继续讲一讲,继承作为类的一大特性之一,能够解决更多的代码耦合的问题,比如同样是学生,男同学和女同学在吃上面也是不一样的,男同学吃饭量大且大口朵颐,女同学量小还温柔细嚼慢咽。这个时候,如果我们在学生类的方法吃里面进行男女生判断再执行不同的操作,如下<?php/** * Student.php * 这是一个学生类,类名 Student和文件名Student一致 * 方便读懂和找类的时候更容易找到和区分 *//** * 类声明的基本形式如下 * class 类名 {} */class Student { // 身高 public $height; // 体重 public $weight; // 性别 public $sex; /** * 每个类都可以声明定义一个构造函数 * 构造函数在实例化的时候就会调用 * 也就是比其他方法会先调用 * 可以接受参数 */ public function __construct($sex) { // 在类内部使用 $this 来访问属性和方法 // 访问类属性和方法时的使用方法时:$类对象名->属性或方法,例如下面 $this->sex = $sex; // 把传进来的性别参数赋值给类的sex属性 } /** * 吃 */ public function eat() { // 根据性别不同来判断吃相 if ( $this->sex == '男' ) { echo '吃得很香,大口朵颐,毫无人性'; } elseif ( $this->sex == '女' ) { echo '哇,温柔的细嚼慢咽,好美的画面'; } else { echo '夹起,塞嘴里,嚼碎,吞咽'; } } /** * 喝 */ public function drink() { echo 'Drinking too much~!'; }}
突然,需求变了,不是男女来区分吃的方法方式了,而是年级来分,一年级的这么吃,二年级的那么吃...去改代码去吧,不仅要去掉先前的代码,还要新增别的代码,并且,万一原来别的地方使用了男、女吃的方法,那可怎么办,隐患真大,所以我们伟大的先人们发明了类继承<?php/** * Student.php * 这是一个学生类,类名 Student和文件名Student一致 * 方便读懂和找类的时候更容易找到和区分 *//** * 类声明的基本形式如下 * class 类名 {} */class Student { // 身高 public $height; // 体重 public $weight; /** * 吃 */ public function eat() { echo 'I am eatting~!'; } /** * 喝 */ public function drink() { echo 'Drinking too much~!'; }}
然后新建男学生类和女学生类(php里面类的继承是只能继承一个父类的)<?phprequire 'Student.php';/** * StudentBoy.php * 男学生类 * 继承学生类,也就继承了学生类的所有非私有(private)的属性和方法 */class StudentBoy extends Student {}
<?phprequire 'Student.php';/** * StudentGirl.php * 女学生类 * 继承学生类,也就继承了学生类的所有非私有(private)的属性和方法 */class StudentGirl extends Student {}
使用关键字 extends 来继承类,这样,啥也不用写啥也不用干,就拥有了学生类的所有非私有(private)属性和方法。<?php/** * class.php */// 包含类文件,也就包含了类require 'StudentBoy.php';// 实例化男学生类对象,虽然男学生类没有eat方法,但是继承了学生类,也继承了学生类的eat方法$boy = new StudentBoy();$boy->eat();
那么继承有了,我们怎么才能够实现不同的性别或年级来执行不同的吃法呢?没错~!(达叔好久不加你...)就是一个叫子类重写父类成员方法的方式,也叫覆盖、覆写。很简单,就是在子类里面重新定义或声明一遍父类的某个方法,这样一来,你实例化子类对象的时候,调用该方法,就会调用子类里面的,那些没有重写父类方法和父类本身的类,依旧可以轻松调用父类的该方法,互不影响,实现解构,解耦。<?phprequire 'Student.php';/** * StudentBoy.php * 男学生类 * 继承学生类,也就继承了学生类的所有非私有(private)的属性和方法 */class StudentBoy extends Student { // 重写父类eat方法 public function eat() { echo '吃得很香,大口朵颐,毫无人性'; }}
<?phprequire 'Student.php';/** * StudentGirl.php * 女学生类 * 继承学生类,也就继承了学生类的所有非私有(private)的属性和方法 */class StudentGirl extends Student { // 重写父类eat方法 public function eat() { echo '哇,温柔的细嚼慢咽,好美的画面'; }}
就非常方便的能扩展了,并且任何一个类修改将不影响父类,父类修改也不影响子类,新增多少个年级的吃法都是新增某个年级的类,然后重写父类的方法即可。关键词:入门