至尊技术网 - MySQL https://www.zzwws.cn/tag/MySQL/ MySQL 小数类型 https://www.zzwws.cn/archives/6386/ 2022-12-28T15:53:00+08:00 定点数decimal能够保证数据精确的小数(小数部分可能不精确,超出长度会四舍五入),整数部分一定精确decimal(M, D), M表示总长度,最大值不能超过65,D代表小数部分长度,最长不能超过30浮点型又称为精度类型,是一种可能丢失精度的数据类型,数据可能不那么准确float 单精度类型4字节存储,7位精度,表示数据范围比整数大得多float 表示不指定小数位的浮点数float(M, D)表示一共存储M个有效数字,其中小数部分占D位double 双精度类型8个字节存储,表示范围更大,精度有15位左右double 表示不指定小数位的浮点数double(M, D)表示一共存储M个有效数字,其中小数部分占D位如何选择当需要存储的小数对精度要求不高时,可以选择FLOAT单精度浮点型,可以节省内存空间,提高计算速度。当需要进行高速数学计算、科学计算、卫星定位计算等对精度要求较高时,可以选择DOUBLE双精度浮点型。当需要进行精确计算,如工资结算、转账打款等财务类型的数据,可以选择DECIMAL定点型。 PHP面向对象封装MySQL PDO(已使用预处理) https://www.zzwws.cn/archives/6343/ 2022-06-10T11:38:00+08:00 Mysql.class.php<?php class Mysql { public $link; public function __construct() { $this->conn(); } /** * 连接数据库,从配置文件读取配置信息 */ public function conn() { $cfg = require 'config.php'; try { $this->link = new PDO("mysql:dbname={$cfg['databaseName']};host={$cfg['host']};charset={$cfg['charset']};port={$cfg['port']}", $cfg['name'], $cfg['password']); $this->link->setAttribute(PDO::ATTR_EMULATE_PREPARES, false); // 设置禁止本地模拟prepare //$db->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);// 设置捕获异常 } catch (PDOException $e) { die("Error: " . $e->getMessage()); } } /** * 查询多行数据 * @param string $table 表名字 * @param string $where where条件 * @param string $field 字段 * @param string $additional 附加sql语句 * @return array */ public function getAll($table, $where = [], $field = "*", $additional = '') { if (strpos($field, ",") !== false) { $arr = explode(",", $field); $str = ''; foreach ($arr as $v) { $str .= "`{$v}`,"; } $field = substr($str, 0, -1); } else if ($field != "*") { $field = "`{$field}`"; } $sql = "SELECT {$field} FROM `{$table}`"; $sql2 = ''; $value = []; if ($where) { if (!is_array($where[0])) { if (strtolower($where[1]) == 'in') { $where[1] = 'IN'; $sql2 = " `{$where[0]}` {$where[1]} ("; if (is_array($where[2])) { foreach ($where[2] as $v) { $value[] = $v; $sql2 .= '?,'; } } else { $value[] = $where[2]; $sql2 .= '?'; } $sql2 = rtrim($sql2, ',') . ')'; } else { $value[] = $where[2]; $sql2 = " `{$where[0]}` {$where[1]} ?"; } } else { foreach ($where as $v) { if (strtolower($v[1]) == 'in') { $v[1] = 'IN'; $sql2 .= " `{$v[0]}` {$v[1]} ("; if (is_array($v[2])) { foreach ($v[2] as $v2) { $value[] = $v2; $sql2 .= "?,"; } } else { $value[] = $v[2]; $sql2 .= "?"; } $sql2 = rtrim($sql2, ',') . ') AND'; } else { $value[] = $v[2]; $sql2 .= " `{$v[0]}` {$v[1]} ? AND"; } } $sql2 = substr($sql2, 0, -4); } if ($sql2) { $sql .= " WHERE " . $sql2; } } if ($additional) { $sql .= ' ' . $additional; } $res = $this->link->prepare($sql); $res->execute($value); $data = $res->fetchAll(PDO::FETCH_ASSOC); return $data; } /** * 查询单行数据 * @param string $table 表名字 * @param string $where where条件 * @param string $field 字段 * @param string $additional 附加sql语句 * @return array */ public function getRow($table, $where = [], $field = "*", $additional = '') { if (strpos($field, ",") !== false) { $arr = explode(",", $field); $str = ''; foreach ($arr as $v) { $str .= "`{$v}`,"; } $field = substr($str, 0, -1); } else if ($field != "*") { $field = "`{$field}`"; } $sql = "SELECT {$field} FROM `{$table}`"; $sql2 = ''; $value = []; if ($where) { if (!is_array($where[0])) { if (strtolower($where[1]) == 'in') { $where[1] = 'IN'; $sql2 = " `{$where[0]}` {$where[1]} ("; if (is_array($where[2])) { foreach ($where[2] as $v) { $value[] = $v; $sql2 .= '?,'; } } else { $value[] = $where[2]; $sql2 .= '?'; } $sql2 = rtrim($sql2, ',') . ')'; } else { $value[] = $where[2]; $sql2 = " `{$where[0]}` {$where[1]} ?"; } } else { foreach ($where as $v) { if (strtolower($v[1]) == 'in') { $v[1] = 'IN'; $sql2 .= " `{$v[0]}` {$v[1]} ("; if (is_array($v[2])) { foreach ($v[2] as $v2) { $value[] = $v2; $sql2 .= "?,"; } } else { $value[] = $v[2]; $sql2 .= "?"; } $sql2 = rtrim($sql2, ',') . ') AND'; } else { $value[] = $v[2]; $sql2 .= " `{$v[0]}` {$v[1]} ? AND"; } } $sql2 = substr($sql2, 0, -4); } if ($sql2) { $sql .= " WHERE " . $sql2; } } if ($additional) { $sql .= ' ' . $additional; } $res = $this->link->prepare($sql); $res->execute($value); $data = $res->fetch(PDO::FETCH_ASSOC); return $data; } /** * 自动创建sql语句并执行 * @param string $table 表名字 * @param array $data 关联数组 键/值与表的列/值对应 * @param string $act 1为insert,2为update * @param array $where 条件,用于update * @return int 成功为insert产生的主键值,update是影响的行数,失败为0 */ public function exec($table, $data, $act = 1, $where = []) { $value = []; if ($act == 1) { $sql = "INSERT INTO `{$table}` (`"; $sql .= implode('`,`', array_keys($data)) . '`)'; $str = ''; foreach ($data as $v) { $str .= "?,"; } $str = substr($str, 0, -1); $sql .= " VALUES ({$str})"; $value = array_values($data); } else { $sql = "UPDATE `{$table}` SET "; foreach ($data as $k => $v) { $sql .= "`" . $k . '`= ' . " ?,"; $value[] = $v; } $sql = rtrim($sql, ','); $sql2 = ''; if ($where) { if (!is_array($where[0])) { if (strtolower($where[1]) == 'in') { $where[1] = 'IN'; $sql2 = " `{$where[0]}` {$where[1]} ("; if (is_array($where[2])) { foreach ($where[2] as $v) { $value[] = $v; $sql2 .= '?,'; } } else { $value[] = $where[2]; $sql2 .= '?'; } $sql2 = rtrim($sql2, ',') . ')'; } else { $value[] = $where[2]; $sql2 = " `{$where[0]}` {$where[1]} ?"; } } else { foreach ($where as $v) { if (strtolower($v[1]) == 'in') { $v[1] = 'IN'; $sql2 .= " `{$v[0]}` {$v[1]} ("; if (is_array($v[2])) { foreach ($v[2] as $v2) { $value[] = $v2; $sql2 .= "?,"; } } else { $value[] = $v[2]; $sql2 .= "?"; } $sql2 = rtrim($sql2, ',') . ') AND'; } else { $value[] = $v[2]; $sql2 .= " `{$v[0]}` {$v[1]} ? AND"; } } $sql2 = substr($sql2, 0, -4); } if ($sql2) { $sql .= " WHERE " . $sql2; } } } $res = $this->link->prepare($sql); $run = $res->execute($value); if ($run) { if ($act == 1) { return $this->link->lastInsertId(); } else { return $res->rowCount(); } } else { return 0; } } /** * 删除数据 * @param string $table 表名字 * @param array $where where条件 * @return bool */ public function delete($table, $where = []) { $sql = "DELETE FROM `{$table}`"; $sql2 = ''; $value = []; if ($where) { if (!is_array($where[0])) { if (strtolower($where[1]) == 'in') { $where[1] = 'IN'; $sql2 = " `{$where[0]}` {$where[1]} ("; if (is_array($where[2])) { foreach ($where[2] as $v) { $value[] = $v; $sql2 .= '?,'; } } else { $value[] = $where[2]; $sql2 .= '?'; } $sql2 = rtrim($sql2, ',') . ')'; } else { $value[] = $where[2]; $sql2 = " `{$where[0]}` {$where[1]} ?"; } } else { foreach ($where as $v) { if (strtolower($v[1]) == 'in') { $v[1] = 'IN'; $sql2 .= " `{$v[0]}` {$v[1]} ("; if (is_array($v[2])) { foreach ($v[2] as $v2) { $value[] = $v2; $sql2 .= "?,"; } } else { $value[] = $v[2]; $sql2 .= "?"; } $sql2 = rtrim($sql2, ',') . ') AND'; } else { $value[] = $v[2]; $sql2 .= " `{$v[0]}` {$v[1]} ? AND"; } } $sql2 = substr($sql2, 0, -4); } if ($sql2) { $sql .= " WHERE " . $sql2; } } $res = $this->link->prepare($sql); return $res->execute($value); } /** * count数据 * @param string $table 表名字 * @param array $where where条件 * @param string $field 字段 * @return int */ public function count($table, $where = [],$field = '*') { $sql = "SELECT COUNT({$field}) FROM `{$table}`"; $sql2 = ''; $value = []; if ($where) { if (!is_array($where[0])) { if (strtolower($where[1]) == 'in') { $where[1] = 'IN'; $sql2 = " `{$where[0]}` {$where[1]} ("; if (is_array($where[2])) { foreach ($where[2] as $v) { $value[] = $v; $sql2 .= '?,'; } } else { $value[] = $where[2]; $sql2 .= '?'; } $sql2 = rtrim($sql2, ',') . ')'; } else { $value[] = $where[2]; $sql2 = " `{$where[0]}` {$where[1]} ?"; } } else { foreach ($where as $v) { if (strtolower($v[1]) == 'in') { $v[1] = 'IN'; $sql2 .= " `{$v[0]}` {$v[1]} ("; if (is_array($v[2])) { foreach ($v[2] as $v2) { $value[] = $v2; $sql2 .= "?,"; } } else { $value[] = $v[2]; $sql2 .= "?"; } $sql2 = rtrim($sql2, ',') . ') AND'; } else { $value[] = $v[2]; $sql2 .= " `{$v[0]}` {$v[1]} ? AND"; } } $sql2 = substr($sql2, 0, -4); } if ($sql2) { $sql .= " WHERE " . $sql2; } } $res = $this->link->prepare($sql); $res->execute($value); $data = $res->fetch(PDO::FETCH_NUM); return $data[0]; } } config.php<?php return array( 'host' => 'localhost', 'name' => 'root', 'password' => 'root', 'databaseName' => 'cs_cn', 'port' => '3306', 'charset' => 'utf8' ); 使用方法<?php require 'Mysql.class.php'; $mysql = new Mysql(); // 添加 $data = [ 'code' => mt_rand(1000000000,9999999999), 'url' => 'https://www.zzwws.cn', 'ip' => mt_rand(1000000000,9999999999), 'add_time' => time() ]; $res = $mysql->exec('zz_url',$data); if($res){ echo '添加成功'; }else{ echo '添加失败'; } // 修改 $data = [ 'code' => mt_rand(1000000000,9999999999) ]; $where = ['id','=',51]; // 或者 // $where = [ // ['id','=',51], // ['ip','=','3755406202'] // ]; $res = $mysql->exec('zz_url',$data,2,$where); if($res){ echo '修改成功'; }else{ echo '修改失败'; } // 查询一行数据 $row = $mysql->getRow('zz_url',['id','=',51],'id,code'); if(!$row){ echo '获取失败'; } print_r($row); // 查询多行数据 $rows = $mysql->getAll('zz_url'); print_r($rows); // 删除 $where = [ ['id','=',52] ]; // 或者 // $where = [ // ['id','in',[1,2,3]] // ]; $res = $mysql->delete('zz_url',$where); var_dump($res); // count $count = $mysql->count('zz_url',['url','=','https://www.zzwws.cn']); var_dump($count); // query方法(没有预处理) $res = $mysql->link->query("SELECT * FROM zz_url WHERE id = '1'"); $row = $res->fetch(PDO::FETCH_ASSOC); print_r($row); MySQL数据库导入sql提示 Unknown collation: ‘utf8mb4_0900_ai_ci‘ https://www.zzwws.cn/archives/5946/ 2021-10-19T15:43:53+08:00 错误原因:高版本数据库(8.0)转存sql文件 并导入低版本数据库(5.6)解决办法:方案一:升级MySQL至高版本方案二:将需要导入的sql文件,把其中的utf8mb4_0900_ai_ci全部替换为utf8mb4_unicode_ci或者utf8mb4_general_ci,重新执行sql文件 从零开始带你成为MySQL实战优化高手 https://www.zzwws.cn/archives/5716/ 2021-09-04T18:59:01+08:00 下载地址:https://www.aliyundrive.com/s/LCANSeEhMhU PHP防止SQL注入 https://www.zzwws.cn/archives/5551/ 2021-08-14T21:02:00+08:00 SQL注入的万能语句' or 1=1#当我们在用户名处输入' or 1=1#,密码随便写,把它带入到语句中,就变成了select * from user where uername='' or1=1#' and password='123456' 在SQL语句中#是注释符,所以后面的语句都会被注释掉select * from user where username='' or1=1 也就是说可以用 'or 1=1# 这么一个字符串就可以绕开登录的密码,直接进入程序,防止这种情况出现,可以使用以下的预处理机制!使用 PDO1、通过传递一个插入值的数组执行一条预处理语句$st = $db->prepare('select * from zz_order where id = ? and name = ?'); $st->execute([$id,$name]);// 成功时返回 true,失败时返回 false $data = $st->fetch(PDO::FETCH_ASSOC); print_r($data); 2、在 prepare 函数里面把参数用 ‘:name’ 这样的形式来替代,然后使用 execute 绑定参数。$st = $db->prepare('select * from zz_order where id = :id'); $st->execute([':id' => $id]); $data = $st->fetch(PDO::FETCH_ASSOC); print_r($data); 3、通过绑定 PHP 变量执行一条预处理语句$st = $db->prepare("select * from zz_order where id = ?"); $st->bindParam(1, $id); $st->execute(); $data = $st->fetchAll(PDO::FETCH_ASSOC); print_r($data); 使用 Mysqli在 prepare 函数里面把参数用 ‘?’ 来替代,然后使用 bind_param 绑定参数。在 bind_param 中,第一个参数 's' 代表了参数的类型与个数(此处为一个字符串类型)。$stmt = $db->prepare('SELECT * FROM employees WHERE name = ?'); $stmt->bind_param('s', $name); $stmt->execute(); $result = $stmt->get_result(); while ($row = $result->fetch_assoc()) { // do something with $row } //bind_param参数类型 i - integer(整型) d - double(双精度浮点型) s - string(字符串) b - BLOB(布尔值) PDO需要注意的是使用PDO去访问MySQL数据库时,真正的prepared statements默认情况下是不使用的。为了解决这个问题,你需要禁用模拟的prepared statements。下面是使用PDO创建一个连接的例子:try { $db = new PDO('mysql:dbname=cs_cn;host=127.0.0.1;charset=utf8', 'root', 'root'); $db->setAttribute(PDO::ATTR_EMULATE_PREPARES, false);// 设置禁止本地模拟prepare //$db->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);// 设置捕获异常 } catch (PDOException $e) { die("Error!: " . $e->getMessage() . "<br/>"); } ThinkPHP防止sql注入:https://www.zzwws.cn/archives/5488/ mysql插入数字都变成2147483647的解决方法 https://www.zzwws.cn/archives/5487/ 2021-08-05T10:53:00+08:00 在用Excel导入数据的时候,碰到11位的数字都变成2147483647,原因是int类型的数据,最大只能到2147483647,所以11位的都变成了2147483647,解决办法:把字段类型由int改为bigint,就可以了.下面是mysql的数据类型详解1.整型(xxxint)MySQL数据类型含义tinyint(m)1个字节表示(-128~127)smallint(m)2个字节表示(-32768~32767)mediumint(m)3个字节表示(-8388608~8388607)int(m)4个字节表示(-2147483648~2147483647)bigint(m)8个字节表示(+-9.22*10的18次方)2.浮点型(float和double)MySQL数据类型含义float(m,d)单精度浮点型,8位精度(4字节),m是十进制数字的总个数,d是小数点后面的数字个数double(m,d)双精度浮点型,16位精度(8字节)参数m只影响显示效果,不影响精度,d却不同,会影响到精度。比如设一个字段定义3.定点数(decimal) decimal(m,d) 定点类型浮点型在数据库中存放的是近似值,而定点类型在数据库中存放的是精确值。参数m是定点类型数字的最大个数(精度),范围为0~65,d小数点右侧数字的个数,范围为0~30,但不得超过m。对定点数的计算能精确到65位数字。 4.字符串(char,varchar,xxxtext)MySQL数据类型含义char(n)固定长度的字符串,最多255个字符varchar(n)固定长度的字符串,最多65535个字符tinytext可变长度字符串,最多255个字符text可变长度字符串,最多65535个字符mediumtext可变长度字符串,最多2的24次方-1个字符longtext可变长度字符串,最多2的32次方-1个字符5.二进制数据(xxxBlob) XXXBLOB和xxxtext是对应的,不过存储方式不同,xxxTEXT是以文本方式存储的,如果存储英文的话区分大小写,而xxxBlob是以二进制方式存储的,不区分大小写。xxxBlob存储的数据只能整体读出。xxxTEXT可以指定字符集,xxxblob不用指定字符集。 6.日期时间类型(date,time,datetime,timestamp)MySQL数据类型含义date日期'2008-12-2'time时间'12:25:36'datetime日期时间'2008-12-2 22:06:44'timestamp不固定timestamp比较特殊,如果定义一个字段的类型为timestamp,这个字段的时间会在其他字段修改的时候自动刷新。所以这个数据类型的字段可以存放这条记录最后被修改的时间,而不是真正来的存放时间。 7.数据类型的属性MySQL关键字含义NULL数据列可包含NULL值NOT NULL数据列不允许包含NULL值DEFAULT xxx默认值,如果插入记录的时候没有指定值,将取这个默认值PRIMARY KEY主键AUTO_INCREMENT递增,如果插入记录的时候没有指定值,则在上一条记录的值上加1,仅适用于整数类型UNSIGNED无符号CHARACTER SET name指定一个字符集 PHP查询大量数据内存耗尽问题的解决方法 https://www.zzwws.cn/archives/5040/ 2021-05-10T15:28:38+08:00 从数据库查询大量数据时会出现内容不够的提示:PHP Fatal error: Allowed memory size of 268 435 456 bytes exhausted 这个问题在PHP的官方网站上叫缓冲查询和非缓冲查询(Buffered and Unbuffered queries)。PHP的查询缺省模式是缓冲模式。也就是说,查询数据结果会一次全部提取到内存里供PHP程序处理。这样给了PHP程序额外的功能,比如说,计算行数,将指针指向某一行等。更重要的是程序可以对数据集反复进行二次查询和过滤等操作。但这种缓冲查询模式的缺陷就是消耗内存,也就是用空间换速度。相对的,另外一种PHP查询模式是非缓冲查询,数据库服务器会一条一条的返回数据,而不是一次全部返回,这样的结果就是PHP程序消耗较少的内存,但却增加了数据库服务器的压力,因为数据库会一直等待PHP来取数据,一直到数据全部取完。很显然,缓冲查询模式适用于小数据量查询,而非缓冲查询适应于大数据量查询。对于PHP的缓冲模式查询大家都知道,下面列举的例子是如何执行非缓冲查询API。非缓冲查询方法一: mysqli<?php $mysqli = new mysqli("localhost", "my_user", "my_password", "world"); $uresult = $mysqli->query("SELECT Name FROM City", MYSQLI_USE_RESULT); if ($uresult) { while ($row = $uresult->fetch_assoc()) { echo $row['Name'] . PHP_EOL; } } $uresult->close(); ?> 非缓冲查询方法二: pdo_mysql<?php $pdo = new PDO("mysql:host=localhost;dbname=world", 'my_user', 'my_pass'); $pdo->setAttribute(PDO::MYSQL_ATTR_USE_BUFFERED_QUERY, false); $uresult = $pdo->query("SELECT Name FROM City"); if ($uresult) { while ($row = $uresult->fetch(PDO::FETCH_ASSOC)) { echo $row['Name'] . PHP_EOL; } } ?> 非缓冲查询方法三: mysql<?php $conn = mysql_connect("localhost", "my_user", "my_pass"); $db = mysql_select_db("world"); $uresult = mysql_unbuffered_query("SELECT Name FROM City"); if ($uresult) { while ($row = mysql_fetch_assoc($uresult)) { echo $row['Name'] . PHP_EOL; } } ?> PHP面向对象封装MySQL操作函数、文件上传 https://www.zzwws.cn/archives/4997/ 2021-01-04T17:36:00+08:00 Mysql.class.php<?php class Mysql { public $link; public function __construct() { $this->conn(); } /** * 连接数据库,从配置文件读取配置信息 */ public function conn() { $cfg = require 'config.php'; $this->link = new mysqli($cfg['host'], $cfg['name'], $cfg['password'], $cfg['databaseName'], $cfg['port']); $this->query('set names ' . $cfg['charset']); } /** * 发送query查询 * @param string $sql sql语句 * @return mixed */ public function query($sql) { return $this->link->query($sql); } /** * 查询多行数据 * @param string $sql sql语句 * @return array */ public function getAll($sql) { $res = $this->query($sql); $data = []; while ($row = $res->fetch_assoc()) { $data[] = $row; } return $data; } /** * 查询单行数据 * @param string $sql sql语句 * @return array */ public function getRow($sql) { $res = $this->query($sql); return $res->fetch_assoc(); } /** * 查询单个数据 * @param string $sql sql语句 * @return array mixed */ public function getOne($sql) { $res = $this->query($sql); return $res->fetch_row()[0]; } /** * 自动创建sql语句并执行 * @param string $table 表名字 * @param array $data 关联数组 键/值与表的列/值对应 * @param string $act 动作/update/insert * @param string $where 条件,用于update * */ public function exec($table, $data, $act = 'insert', $where = '0') { if ($act == 'insert') { //插入语句 insert into 表名 (字段1,字段2) values ('values1','values2') $sql = "insert into $table ("; $sql .= implode(',', array_keys($data)) . ')'; $sql .= " values ('"; $sql .= implode("','", array_values($data)) . "')"; } else { //修改语句 update 表名 set 字段1='values1',字段2='values2' where id=1 $sql = "update $table set "; foreach ($data as $k => $v) { $sql .= $k . '=' . "'$v',"; } $sql = rtrim($sql, ','); $sql .= " where $where"; } return $this->query($sql); } /** * 返回上一条insert语句产生的主键值 */ public function lastId() { return $this->link->insert_id; } /** * 返回上一条语句影响的行数 */ public function affectRows() { return $this->link->affected_rows; } } Upload.class.php<?php abstract class AUpload { public $allowext = array('jpg', 'jpeg', 'png', 'rar'); public $maxsize = 1; protected $error = ''; abstract public function getInfo($name); abstract public function createDir(); abstract public function randStr($len = 8); abstract protected function checkType($ext); abstract protected function checkSize($size); abstract public function up($name); public function getError() { return $this->error; } } class Upload extends AUpload { /** * 分析$_FILES中$name域的信息,比如$_FILES['pic'] * @param string $name 表单中的file里的name值 * @return array 上传文件的信息 */ public function getInfo($name) { return $_FILES[$name]; } /** * 创建目录 /upload/2021/01/04 * @return string 目录路径 */ public function createDir() { $dir = '/upload/' . date('Y/m/d'); if (!is_dir($dir)) { mkdir($dir, 0777, true); } return $dir; } /** * 生成随机字符串 * @param int $len 随机字符串的长度 * @return string 返回生成的字符串 */ public function randStr($len = 6) { $str = str_shuffle('abcedfghjkmnpqrstuvwxyzABCEDFGHJKMNPQRSTUVWXYZ0123456789'); return substr($str, 0, $len); } /** * 检查文件类型 * @param $ext 文件后缀 * @return boolean */ protected function checkType($ext) { return in_array($ext, $this->allowext); } /** * 检测文件大小 * @param $size 文件大小 * @return boolean */ protected function checkSize($size) { return $size < $this->maxsize * 1024 * 1024; } /** * 上传文件 * @param string $name 表单中file的name值 * @return string 上传的文件,如/upload/2021/01/04/1609749834kfyzXr.jpg */ public function up($name) { if (!isset($_FILES[$name])) { echo '没有上传文件';exit(); } $info = $this->getInfo($name); $ext = ltrim(strrchr($info['name'], '.'), '.'); if (!$this->checkType($ext)) { echo '不允许上传此类型文件';exit(); } if (!$this->checkSize($info['size'])) { echo '文件过大';exit(); } $dir = $this->createDir(); $filename = time() . $this->randStr() . '.' . $ext; if (move_uploaded_file($info['tmp_name'], $dir . '/' . $filename)) { $data['path'] = $dir; $data['filename'] = $filename; return $data; } else { echo '上传失败'; } } } $file = new Upload(); var_dump($file->up('pic')); upload.html<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title>上传</title> </head> <body> <form action="Upload.class.php" method="post" enctype="multipart/form-data"> <input type="file" name="pic"> <button type="submit" id="submit">提交</button> </form> </body> </html> config.php<?php return array( 'host' => 'localhost', 'name' => 'cs', 'password' => '123456', 'databaseName' => 'cs', 'port' => '3306', 'charset' => 'utf8' ); 使用方法$mysql = new Mysql(); 1、增$art['title'] = trim($_POST['title']); $art['cat_id'] = trim($_POST['cat_id']); $art['content'] = trim($_POST['content']); $art['pubtime'] = time(); if ($mysql->exec('art', $art)) { echo('添加成功'); } else { echo('添加失败'); } 2、删$sql = "delete from cat where cat_id='$cat_id'"; if ($mysql->query($sql)) { echo('删除成功'); } else { echo('删除失败'); } 3、改$cat_id = $_GET['cat_id']; $cat['catname'] = trim($_POST['catname']); if ($mysql->exec('cat',$cat,'update',"cat_id=$cat_id")) { echo('修改成功'); } else { echo('修改失败'); } 4、查查询多行数据$sql = "select * from cat"; $arr = $mysql->getAll($sql); print_r($arr); 取出一行数据$sql = "select * from cat where cat_id='$cat_id'"; if (!$mysql->getRow($sql)) { echo('栏目不存在'); exit(); } 查询返回一个结果$sql = "select * from cat where cat_id='$cat_id'"; echo $mysql->getOne($sql); 获取上一步insert 操作产生的主键id$mysql->lastId(); MySQL中varchar与char的区别 https://www.zzwws.cn/archives/4966/ 2020-12-05T10:08:08+08:00 区别一,定长和变长char 表示定长,长度固定,varchar表示变长,即长度可变。char如果插入的长度小于定义长度时,则用空格填充;varchar小于定义长度时,还是按实际长度存储,插入多长就存多长。因为其长度固定,char的存取速度还是要比varchar要快得多,方便程序的存储与查找;但是char也为此付出的是空间的代价,因为其长度固定,所以会占据多余的空间,可谓是以空间换取时间效率。varchar则刚好相反,以时间换空间。区别之二,存储的容量不同对 char 来说,最多能存放的字符个数 255,和编码无关。而 varchar 呢,最多能存放 65532 个字符。varchar的最大有效长度由最大行大小和使用的字符集确定。整体最大长度是 65,532字节。 PHP 封装MySQL操作函数、魔术常量、封装函数 https://www.zzwws.cn/archives/4964/ 2020-12-02T09:49:00+08:00 mysql.php<?php /** * mysql.php mysql系列操作函数 * @author nianbaibai */ /** * 连接数据库 * * @return resource 连接成功,返回连接数据库的资源 */ function mConn() { static $conn = null; if ($conn === null) { $db = require ROOT . '/lib/config.php'; $conn = mysqli_connect("$db[host]", "$db[name]", "$db[password]", "$db[databaseName]", "$db[port]"); mysqli_query($conn, 'set names ' . $db['charset']); } return $conn; } /** * 查询的函数 * @return mixed resoure/bool */ function mQuery($sql) { $rs = mysqli_query(mConn(), $sql); if ($rs) { // mLog($sql);//执行成功的日志,如果需要的可以显示这段 } else { mLog($sql . "\n" . mysqli_error(mConn())); } return $rs; } /** * log日志记录功能 * @param str $str 待记录的字符串 */ function mLog($str) { $filename = ROOT . '/log/' . date('Ymd') . '.txt'; $log = "-----------------------------------------\n" . date('Y/m/d H:i:s') . "\n" . $str . "\n" . "-----------------------------------------\n\n"; return file_put_contents($filename, $log, FILE_APPEND); } /** * select 查询多行数据 * * @param str $sql select 待查询的sql语句 * @return mixed select 查询成功,返回二维数组,失败返回false */ function mGetAll($sql) { $rs = mQuery($sql); if (!$rs) { return false; } $data = array(); while ($row = mysqli_fetch_assoc($rs)) { $data[] = $row; } return $data; } /*$sql = "select * from cat"; print_r(mGetAll($sql)); */ /** * select 取出一行数据 * * @param str $sql 待查询的sql语句 * @return arr/false 查询成功 返回一个一维数组 */ function mGetRow($sql) { $rs = mQuery($sql); if (!$rs) { return false; } return mysqli_fetch_assoc($rs); } /*$sql = "select * from cat where cat_id=1"; print_r(mGetRow($sql));*/ /** * select 查询返回一个结果 * * @param str $sql 待查询的select语句 * @return mixed 成功,返回结果,失败返回false */ function mGetOne($sql) { $rs = mQuery($sql); if (!$rs) { return false; } return mysqli_fetch_row($rs)[0]; } /*$sql = "select count(*) from art where cat_id=1"; echo mGetOne($sql);*/ /** * 自动拼接insert 和 update sql语句,并且调用mQuery() 去执行sql * * @param str $table 表名 * @param arr $data 接收到的数据,一维数组 * @param str $act 动作 默认为'insert' * @param str $where 防止update更改时少加where条件 * @return bool insert 或者update 插入成功或失败 */ function mExec($table, $data, $act = 'insert', $where = 0) { if ($act == 'insert') { $sql = "insert into $table ("; $sql .= implode(',', array_keys($data)) . ") values ('"; $sql .= implode("','", array_values($data)) . "')"; return mQuery($sql); } else if ($act == 'update') { $sql = "update $table set "; foreach ($data as $k => $v) { $sql .= $k . "='" . $v . "',"; } $sql = rtrim($sql, ',') . " where " . $where; return mQuery($sql); } } //$data = array('title'=>'今天的空气' , 'content'=>'空气质量优' , 'pubtime'=>12345678,'author'=>'baibai'); //insert into art (title,content,pubtime,author) values ('今天的空气','空气质量优','12345678','baibai'); //update art set title='今天的空气',conte='空气质量优',pubtime='12345678',author='baibai' where art_id=1; //echo mExec('art' , $data , 'update' , 'art_id=1');; //insert into cat (id,catname) values (5 , 'test'); /** * 取得上一步insert 操作产生的主键id */ function getLastId() { return mysqli_insert_id(mConn()); } /** * 使用反斜线 转义字符串 * @param arr 待转义的数组 * @return arr 被转义后的数组 */ function _addslashes($arr) { foreach ($arr as $k => $v) { if (is_string($v)) { $arr[$k] = addslashes($v); } else if (is_array($v)) { $arr[$k] = _addslashes($v); } } return $arr; } config.php<?php //salt为cookie登录的安全码 return array( 'host' => 'localhost', 'name' => 'cs', 'password' => '123456', 'databaseName' => 'cs', 'port' => '3306', 'charset' => 'utf8', 'salt' => 'Q!!RN13q&y' ); func.php<?php /** *@param str $msg 成功返回的信息 *@param str $file 跳转的文件名,返回上一页为-1 *@param int $time 延时跳转的时间,单位秒 */ function succ($msg, $file = '', $time = 1) { $res = 'succ'; require ROOT . '/view/admin/info.html'; if ($file != '') { if ($file == '-1') { // header("Refresh:$time;url=$_SERVER[HTTP_REFERER]"); echo '<script>window.setTimeout(function() {window.history.back(-1);},' . $time . '000)</script>'; } else { header("Refresh:$time;url=$file"); } } exit(); } /** *@param str $msg 失败返回的报错信息 *@param str $file 跳转的文件名,返回上一页为-1 *@param int $time 延时跳转的时间,单位秒 */ function error($msg, $file = '', $time = 1) { $res = 'fail'; require ROOT . '/view/admin/info.html'; if ($file != '') { if ($file == '-1') { // header("Refresh:$time;url=$_SERVER[HTTP_REFERER]"); echo '<script>window.setTimeout(function() {window.history.back(-1);},' . $time . '000)</script>'; } else { header("Refresh:$time;url=$file"); } } exit(); } /** *获取访客IP */ function getRealIp() { static $realip = null; if ($realip !== null) { return $realip; } if (getenv('REMOTE_ADDR')) { $realip = getenv('REMOTE_ADDR'); } else if (getenv('HTTP_CLIENT_IP')) { $realip = getenv('HTTP_CLIENT_IP'); } else if (getenv('HTTP_X_FROWARD_FOR')) { $realip = getenv('HTTP_X_FROWARD_FOR'); } return $realip; } /** * 生成随机字符串 * @param int $num 生成的随机字符串的个数 * @return str 生成的随机字符串 */ function randStr($num = 6) { $str = str_shuffle('abcedfghjkmnpqrstuvwxyzABCEDFGHJKMNPQRSTUVWXYZ0123456789'); return substr($str, 0, $num); } //echo randStr(); /** * 创建目录 ROOT.'/upload/2015/01/25/qwefas.jpg' * @return str 成功返回路径,失败返回false */ function createDir() { $path = '/upload/' . date('Y/m/d'); $fpath = ROOT . $path; if (is_dir($fpath) || mkdir($fpath, 0777, true)) { return $path; } else { return false; } } /** * 获取文件后缀 * @param str $filename 文件名 * @return str 文件的后缀名,且带点. */ function getExt($filename) { return strrchr($filename, '.'); } /** * 检测用户是否登录 * @return bool 已登录返回true,未登录返回false */ function acc() { if (!isset($_COOKIE['name']) || !isset($_COOKIE['ccode'])) { return false; } return $_COOKIE['ccode'] === cCode($_COOKIE['name']); } /** * 加密用户名 * @param str $name 用户登陆时输入的用户名 * @return str md5(用户名+salt)=>md5码 */ function cCode($name) { $salt = require ROOT . '/lib/config.php'; return md5($name . '|' . $salt['salt']); } info.html<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title></title> </head> <body> <div id="rside"> <?php if($res == 'succ'){?> <div class="succ"><?php echo $msg?></div> <?php }else if($res == 'fail'){?> <div class="danger"><?php echo $msg?></div> <?php }?> </div> </body> </html> login.php<?php require 'lib/init.php'; if (acc()) { header('location: artlist.php'); } if (empty($_POST)) { require ROOT . '/view/admin/login.html'; } else { $name = trim($_POST['username']); if ($name == '') { error('用户名不能为空'); } if (!preg_match('/^[A-Za-z0-9_\x{4e00}-\x{9fa5}]+$/u', $name)) { //用户名只能由数字、字母、中文汉字及下划线组成,不能包含特殊符号,在php中,不支持[\u4e00-\u9fa5]匹配汉字,而是用\x表示十六进制数据,然而php中用"[\x4e00-\x9fa5]"的写法也是错的,必须用{}把它包起来才行。此外,由于编码关系,需要用到"/u"声明编码格式。 error('用户名格式不正确'); } $password = trim($_POST['password']); if ($password == '') { error('密码不能为空'); } // $sql = "select * from user where name='$name' and password='$password'"; $sql = "select * from user where name='$name'"; $res = mGetRow($sql); if (!$res) { error('用户名不存在'); } else if (md5($res['salt'] . $password) !== $res['password']) {//这里的salt为密码的安全码,可以在注册成功后生成一个随机的安全码 error('密码错误'); } else { setcookie('name', $res['name']); setcookie('ccode', cCode($res['name'])); header('location: artlist.php'); } } init.php<?php //echo __DIR__,'<br>';//D:\xampp\htdocs\1\Blog //echo __FILE__,'<br>';//D:\xampp\htdocs\1\Blog\init.php //echo __LINE__;//4 header('content-type:text/html;charset=utf8'); define('ROOT', dirname(__DIR__)); //定义个ROOT常量,dirname往上跳一级 require ROOT . '/lib/mysql.php'; require ROOT . '/lib/func.php'; $_GET = _addslashes($_GET); $_POST = _addslashes($_POST); $_COOKIE = _addslashes($_COOKIE); 使用方法首先引入init.php,这里的art和cat是表名,mysqli_query($conn, $sql)可变为mQuery($sql)1、增$art['title'] = trim($_POST['title']); $art['cat_id'] = trim($_POST['cat_id']); $art['content'] = trim($_POST['content']); $art['pubtime'] = time(); if (mExec('art', $art)) { succ('添加成功'); } else { error('添加失败'); } 2、删$sql = "delete from cat where cat_id='$cat_id'"; if (mQuery($sql)) { succ('删除成功'); } else { error('删除失败'); } 3、改$cat_id = $_GET['cat_id']; $cat['catname'] = trim($_POST['catname']); if (mExec('cat',$cat,'update',"cat_id=$cat_id")) { succ('修改成功'); } else { error('修改失败'); } 4、查查询多行数据$sql = "select * from cat"; $arr = mGetAll($sql); print_r($arr); 取出一行数据$sql = "select * from cat where cat_id='$cat_id'"; if (!mGetRow($sql)) { error('栏目不存在'); exit(); } 查询返回一个结果$sql = "select * from cat where cat_id='$cat_id'"; echo mGetOne($sql); 获取上一步insert 操作产生的主键idgetLastId(); 使用反斜线,转义字符串使用方法:在顶部添加一下代码$_GET = _addslashes($_GET); $_POST = _addslashes($_POST); $_COOKIE = _addslashes($_COOKIE); 检测用户是否登录if(!acc()){ header('location: login.php'); } 登录成功后添加name和ccode的cookie,请参考上面的login.phpsetcookie('name', $res['name']); setcookie('ccode', cCode($res['name'])); 退出登录setcookie('name', '', 0); setcookie('ccode', '', 0); header('location: login.php');