thinkphp6结合layui增删改查综合案列
文章目录
- 技术栈
- 实现
- 代码实现
- 数据库
本案例适合新手,特别是杠刚入门thinkphp和layui,但又不是特别熟悉这类
主要实现登录退出功能,用户模块的增删改查功能,分页功能是layui表单自带功能
效果图
左侧的菜单栏我没有写对应的页面,需要的自己添加上就行,把菜单弄出来主要是为了好看一点

目录结构

技术栈
thinkphp6+layui
实现
layui实现后台布局
中间件和session判断用户是否登录
用到think-template模板引擎,安装完tp框架后需要自己安装
composer create-project topthink/think=6.0.x-dev tp
composer require topthink/think-view
ajax请求数据
msyql数据库
代码实现
登录页面,相关的请求方法都写在了页面中
<!DOCTYPE html>
<html lang="en"><head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>登录页面</title><!-- 引入LayUI的CSS文件 --><link rel="stylesheet" href="/layui/css/layui.css"><!-- 引入LayUI的JS文件 --><script src="/layui/layui.js"></script><style>* {margin: 0;padding: 0;box-sizing: border-box;}body {font-family: 'Arial', sans-serif;background-color: #f0f2f5;display: flex;justify-content: center;align-items: center;height: 100vh;}.login-container {width: 450px;padding: 2rem;background-color: #ffffff;border-radius: 5px;box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);}h1 {color: #333333;text-align: center;margin-bottom: 1.5rem;}label {color: #333333;margin-bottom: 0.5rem;}input.layui-input {height: 40px;padding: 0 1rem;margin-bottom: 1.5rem;border: 1px solid #d9d9d9;border-radius: 5px;}button.layui-btn {height: 40px;color: #ffffff;background-color: #3498db;border: none;border-radius: 5px;cursor: pointer;transition: background-color 0.3s ease;}button.layui-btn:hover {background-color: #2980b9;}</style>
</head><body><div class="login-container"><h1>登录</h1><form class="layui-form" action="/admin/index" method="post"><div class="layui-form-item"><label for="username" class="layui-form-label">用户名:</label><div class="layui-input-block"><input type="text" id="username" name="username" placeholder="请输入用户名" required lay-verify="required" autocomplete="off" class="layui-input"></div></div><div class="layui-form-item"><label for="password" class="layui-form-label">密码:</label><div class="layui-input-block"><input type="password" id="password" name="password" placeholder="请输入密码" required lay-verify="required" autocomplete="off" class="layui-input"></div></div><div class="layui-form-item"><div class="layui-input-block"><button class="layui-btn" lay-submit lay-filter="login">登录</button></div></div></form></div><!DOCTYPE html>
<!-- 省略其他代码 --><script>layui.use(['form', 'layer'], function () {var form = layui.form;var layer = layui.layer;form.on('submit(login)', function(data){console.log(data);});});</script>
</body></html>
后台布局,layui.js和layui.css改成自己的
<!DOCTYPE html>
<html><head><meta charset="utf-8"><title>Layui</title><meta name="renderer" content="webkit"><meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1"><meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1"><link rel="stylesheet" href="/layui/css/layui.css" media="all"><!-- 注意:如果你直接复制所有代码到本地,上述css路径需要改成你本地的 -->
</head><body><table class="layui-hide" id="test" lay-filter="test"></table><!-- 定义编辑用户弹层 --><div id="edit-form" style="display:none;"><form class="layui-form" action="" lay-filter="" id="${id}"><div class="layui-form-item"><label class="layui-form-label">Id</label><div class="layui-input-block"><input type="text" name="id" required lay-verify="required" autocomplete="off" class="layui-input" value="..."disabled></div></div><div class="layui-form-item"><label class="layui-form-label">用户名</label><div class="layui-input-block"><input type="text" name="username" required lay-verify="required" autocomplete="off" class="layui-input"value="..."></div></div><div class="layui-form-item"><label class="layui-form-label">邮箱</label><div class="layui-input-block"><input type="text" name="email" required lay-verify="required" autocomplete="off" class="layui-input"value="..."></div></div><div class="layui-form-item"><label class="layui-form-label">地址</label><div class="layui-input-block"><input type="text" name="address" required lay-verify="required" autocomplete="off" class="layui-input"value="..."></div></div><div class="layui-form-item"><div class="layui-input-block"><button class="layui-btn" lay-submit lay-filter="editSubmit">修改</button><button type="reset" class="layui-btn layui-btn-primary">重置</button></div></div></form></div><!-- 新增用户模块弹层 --><div id="add-form" style="display:none;"><form class="layui-form" action=""><div class="layui-form-item"><label class="layui-form-label">用户名</label><div class="layui-input-block"><input type="text" name="username" lay-verify="required" placeholder="请输入用户名" autocomplete="off"class="layui-input"></div></div><div class="layui-form-item"><label class="layui-form-label">邮箱</label><div class="layui-input-block"><input type="text" name="email" lay-verify="required|email" placeholder="请输入邮箱" autocomplete="off"class="layui-input"></div></div><div class="layui-form-item"><label class="layui-form-label">地址</label><div class="layui-input-block"><input type="text" name="address" lay-verify="required" placeholder="请输入地址" autocomplete="off"class="layui-input"></div></div><div class="layui-form-item"></div></form></div><script type="text/html" id="toolbarDemo"><div class="layui-btn-container"><button class="layui-btn layui-btn-sm" lay-event="getCheckData">获取选中行数据</button><button class="layui-btn layui-btn-sm layui-btn-danger" lay-event="getCheckLength">获取选中数目</button><button class="layui-btn layui-btn-sm layui-btn-warm" lay-event="isAll">验证是否全选</button><button class="layui-btn layui-btn-sm layui-btn-normal" lay-event="add">添加用户</button></div>
</script><script type="text/html" id="barDemo"><a class="layui-btn layui-btn-xs" lay-event="edit">编辑</a><a class="layui-btn layui-btn-danger layui-btn-xs" lay-event="del">删除</a>
</script><script src="/layui/layui.js" charset="utf-8"></script><!-- 注意:如果你直接复制所有代码到本地,上述 JS 路径需要改成你本地的 --><script>var userListData = JSON.parse('{:json_encode($userList)}');layui.use('table', function () {var table = layui.table;var $ = layui.jquery;table.render({elem: '#test', data: userListData, toolbar: '#toolbarDemo' //开启头部工具栏,并为其绑定左侧模板, defaultToolbar: ['filter', 'exports', 'print', { //自定义头部工具栏右侧图标。如无需自定义,去除该参数即可title: '提示', layEvent: 'LAYTABLE_TIPS', icon: 'layui-icon-tips'}], title: '用户数据表', cols: [[{ type: 'checkbox', fixed: 'left' },{ field: 'id', title: 'ID', width: 80, fixed: 'left', unresize: true, sort: true, align: 'center' },{ field: 'username', title: '用户名', align: 'center', width: 120 },{ field: 'email', title: '邮箱', align: 'center' },{ field: 'address', title: '地址', align: 'center' },{ fixed: 'right', title: '操作', toolbar: '#barDemo', align: 'center' }]], page: true});//头工具栏事件table.on('toolbar(test)', function (obj) {var checkStatus = table.checkStatus(obj.config.id);switch (obj.event) {case 'getCheckData':var data = checkStatus.data;layer.alert(JSON.stringify(data));break;case 'getCheckLength':var data = checkStatus.data;layer.msg('选中了:' + data.length + ' 个');break;case 'isAll':layer.msg(checkStatus.isAll ? '全选' : '未全选');break;case 'add':layer.open({type: 1,title: '新增用户',content: $('#add-form').html(), // 从页面中获取表单内容area: ['500px', '320px'],btn: ['提交', '取消'],yes: function (index, layero) {// 点击“提交”按钮时的回调函数var data = layero.find('form').serialize();// 发送表单数据到后端$.post('/admin/addUser', data, function (res) {if (res.success) {layer.msg(res.message);// 关闭弹出层layer.close(index);// 重新加载数据表格setTimeout(function () {window.location.reload();}, 2000);table.reload('test', {});} else {layer.msg(res.message);}}).fail(function () {layer.msg('请求失败,请重试');});}});};});//监听行工具事件,删除事件table.on('tool(test)', function (obj) {var data = obj.data;if (obj.event === 'del') {var id = data.id;// 弹出确认框layer.confirm('确定要删除该用户吗?', function (index) {// 用户点击了确定按钮,关闭确认框layer.close(index);// 使用Layui的内置jQuery发送POST请求$.post('/admin/deleteUserById', { id: id }, function (res) {if (res.success) {obj.del(); // 如果删除成功,从表格中删除行} else {layer.msg('删除失败');}}).fail(function () {layer.msg('请求失败,请重试');});});} else {// 弹出编辑层layer.open({type: 1,title: '编辑用户信息',content: $('#edit-form').html(), // 从页面中获取表单内容area: ['500px', '320px'],success: function (layero, index) {// 将用户数据填充到表单元素中layero.find('input[name="id"]').val(data.id);layero.find('input[name="username"]').val(data.username);layero.find('input[name="email"]').val(data.email);layero.find('input[name="address"]').val(data.address);}});}});// 监听编辑表单提交事件layui.form.on('submit(editSubmit)', function (data) {// 发送表单数据到后端$.post('/admin/updateUserById', data.field, function (res) {console.log(res);if (res.success) {layer.msg(res.message);// 关闭弹出层layer.closeAll('page');// 刷新页面重新加载表格setTimeout(function () {window.location.reload();}, 2000);} else {layer.msg('更新失败');}}).fail(function () {layer.msg('请求失败,请重试');});return false; // 阻止表单提交});});</script></body></html>
用户列表
<!DOCTYPE html>
<html><head><meta charset="utf-8"><title>Layui</title><meta name="renderer" content="webkit"><meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1"><meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1"><link rel="stylesheet" href="/layui/css/layui.css" media="all"><!-- 注意:如果你直接复制所有代码到本地,上述css路径需要改成你本地的 -->
</head><body><table class="layui-hide" id="test" lay-filter="test"></table><!-- 定义编辑用户弹层 --><div id="edit-form" style="display:none;"><form class="layui-form" action="" lay-filter="" id="${id}"><div class="layui-form-item"><label class="layui-form-label">Id</label><div class="layui-input-block"><input type="text" name="id" required lay-verify="required" autocomplete="off" class="layui-input" value="..."disabled></div></div><div class="layui-form-item"><label class="layui-form-label">用户名</label><div class="layui-input-block"><input type="text" name="username" required lay-verify="required" autocomplete="off" class="layui-input"value="..."></div></div><div class="layui-form-item"><label class="layui-form-label">邮箱</label><div class="layui-input-block"><input type="text" name="email" required lay-verify="required" autocomplete="off" class="layui-input"value="..."></div></div><div class="layui-form-item"><label class="layui-form-label">地址</label><div class="layui-input-block"><input type="text" name="address" required lay-verify="required" autocomplete="off" class="layui-input"value="..."></div></div><div class="layui-form-item"><div class="layui-input-block"><button class="layui-btn" lay-submit lay-filter="editSubmit">修改</button><button type="reset" class="layui-btn layui-btn-primary">重置</button></div></div></form></div><!-- 新增用户模块弹层 --><div id="add-form" style="display:none;"><form class="layui-form" action=""><div class="layui-form-item"><label class="layui-form-label">用户名</label><div class="layui-input-block"><input type="text" name="username" lay-verify="required" placeholder="请输入用户名" autocomplete="off"class="layui-input"></div></div><div class="layui-form-item"><label class="layui-form-label">邮箱</label><div class="layui-input-block"><input type="text" name="email" lay-verify="required|email" placeholder="请输入邮箱" autocomplete="off"class="layui-input"></div></div><div class="layui-form-item"><label class="layui-form-label">地址</label><div class="layui-input-block"><input type="text" name="address" lay-verify="required" placeholder="请输入地址" autocomplete="off"class="layui-input"></div></div><div class="layui-form-item"></div></form></div><script type="text/html" id="toolbarDemo"><div class="layui-btn-container"><button class="layui-btn layui-btn-sm" lay-event="getCheckData">获取选中行数据</button><button class="layui-btn layui-btn-sm layui-btn-danger" lay-event="getCheckLength">获取选中数目</button><button class="layui-btn layui-btn-sm layui-btn-warm" lay-event="isAll">验证是否全选</button><button class="layui-btn layui-btn-sm layui-btn-normal" lay-event="add">添加用户</button></div>
</script><script type="text/html" id="barDemo"><a class="layui-btn layui-btn-xs" lay-event="edit">编辑</a><a class="layui-btn layui-btn-danger layui-btn-xs" lay-event="del">删除</a>
</script><script src="/layui/layui.js" charset="utf-8"></script><!-- 注意:如果你直接复制所有代码到本地,上述 JS 路径需要改成你本地的 --><script>var userListData = JSON.parse('{:json_encode($userList)}');layui.use('table', function () {var table = layui.table;var $ = layui.jquery;table.render({elem: '#test', data: userListData, toolbar: '#toolbarDemo' //开启头部工具栏,并为其绑定左侧模板, defaultToolbar: ['filter', 'exports', 'print', { //自定义头部工具栏右侧图标。如无需自定义,去除该参数即可title: '提示', layEvent: 'LAYTABLE_TIPS', icon: 'layui-icon-tips'}], title: '用户数据表', cols: [[{ type: 'checkbox', fixed: 'left' },{ field: 'id', title: 'ID', width: 80, fixed: 'left', unresize: true, sort: true, align: 'center' },{ field: 'username', title: '用户名', align: 'center', width: 120 },{ field: 'email', title: '邮箱', align: 'center' },{ field: 'address', title: '地址', align: 'center' },{ fixed: 'right', title: '操作', toolbar: '#barDemo', align: 'center' }]], page: true});//头工具栏事件table.on('toolbar(test)', function (obj) {var checkStatus = table.checkStatus(obj.config.id);switch (obj.event) {case 'getCheckData':var data = checkStatus.data;layer.alert(JSON.stringify(data));break;case 'getCheckLength':var data = checkStatus.data;layer.msg('选中了:' + data.length + ' 个');break;case 'isAll':layer.msg(checkStatus.isAll ? '全选' : '未全选');break;case 'add':layer.open({type: 1,title: '新增用户',content: $('#add-form').html(), // 从页面中获取表单内容area: ['500px', '320px'],btn: ['提交', '取消'],yes: function (index, layero) {// 点击“提交”按钮时的回调函数var data = layero.find('form').serialize();// 发送表单数据到后端$.post('/admin/addUser', data, function (res) {if (res.success) {layer.msg(res.message);// 关闭弹出层layer.close(index);// 重新加载数据表格setTimeout(function () {window.location.reload();}, 2000);table.reload('test', {});} else {layer.msg(res.message);}}).fail(function () {layer.msg('请求失败,请重试');});}});};});//监听行工具事件,删除事件table.on('tool(test)', function (obj) {var data = obj.data;if (obj.event === 'del') {var id = data.id;// 弹出确认框layer.confirm('确定要删除该用户吗?', function (index) {// 用户点击了确定按钮,关闭确认框layer.close(index);// 使用Layui的内置jQuery发送POST请求$.post('/admin/deleteUserById', { id: id }, function (res) {if (res.success) {obj.del(); // 如果删除成功,从表格中删除行} else {layer.msg('删除失败');}}).fail(function () {layer.msg('请求失败,请重试');});});} else {// 弹出编辑层layer.open({type: 1,title: '编辑用户信息',content: $('#edit-form').html(), // 从页面中获取表单内容area: ['500px', '320px'],success: function (layero, index) {// 将用户数据填充到表单元素中layero.find('input[name="id"]').val(data.id);layero.find('input[name="username"]').val(data.username);layero.find('input[name="email"]').val(data.email);layero.find('input[name="address"]').val(data.address);}});}});// 监听编辑表单提交事件layui.form.on('submit(editSubmit)', function (data) {// 发送表单数据到后端$.post('/admin/updateUserById', data.field, function (res) {console.log(res);if (res.success) {layer.msg(res.message);// 关闭弹出层layer.closeAll('page');// 刷新页面重新加载表格setTimeout(function () {window.location.reload();}, 2000);} else {layer.msg('更新失败');}}).fail(function () {layer.msg('请求失败,请重试');});return false; // 阻止表单提交});});</script></body></html>
后端代码
Index.php
这个文件没有什么好说的,就是访问index/index的时候渲染登录页面
<?php
namespace app\controller;
use app\BaseController;
use think\facade\View;class Index extends BaseController
{public function index(){return View::fetch();}public function hello($name = 'ThinkPHP6'){return 'hello,' . $name;}
}
Admin.php控制器
这个控制器中,首先index登录页面请求index方法判断用户名密码,用户名密码正确后渲染后台主页
用户名密码不正确重定向到登录页面
同时增删改查功能也是在这个控制器内完成的,但这些功能都需要经过中间件CheckLogin判断session是否存在,就是用户是否登录
<?php
namespace app\controller;use app\BaseController;
use think\facade\View;
use think\facade\Request;
use app\model\User;
use think\facade\Session;
use app\middleware\CheckLogin;
use app\model\UserList;class admin extends BaseController
{protected $middleware = [CheckLogin::class => ['except' => ['index']]]; //当执行admin控制器的时候就会调用CheckLogin中间件public function index(){$username = Request::post('username');$password = Request::post('password');$res = User::where('username', $username)->find();// 判断用户是否存在,以及密码是否正确if ($res && $res->password == md5($password)) {// 存储用户信息到session中Session::set('res', $res);View::assign('res', $res);return View::fetch();} else {// 密码不正确,重定向到登录页面return redirect('../Index/index')->with('error', '用户名或密码错误');}}public function logout(){session_destroy();return redirect('../Index/index')->with('error', '退出成功');}public function userList(){$list = UserList::select();// 分配数据给模板View::assign('userList', $list);// 渲染模板并返回return View::fetch();}public function deleteUserById(){$id = Request::post('id');$res = UserList::destroy($id);if ($res) {return json(['success' => true, 'message' => '删除成功']);} else {return json(['success' => false, 'message' => '删除失败']);}}public function updateUserById(){$id = Request::post('id');$username = Request::post('username');$email = Request::post('email');$address = Request::post('address');$res = UserList::update(['username'=>$username,'email'=>$email,'address'=>$address,'id' => $id]);try {$res = UserList::update(['username'=>$username,'email'=>$email,'address'=>$address,'id' => $id]);if ($res) {return json(['success' => true, 'message' => '更新成功']);} else {return json(['success' => false, 'message' => '更新失败']);}} catch (\Exception $e) {return json(['success' => false, 'message' => $e->getMessage()]);}}public function addUser(){$res = UserList::create(['username'=>Request::post('username'),'email'=>Request::post('email'),'address'=>Request::post('address')]);if ($res) {return json(['success' => true, 'message' => '添加成功']);} else {return json(['success' => false, 'message' => '添加失败']);}}
}
中间件代码CheckLogin.php代码
<?php
//判断用户是否登录的中间件
namespace app\middleware;use think\facade\Session;class CheckLogin
{public function handle($request,$next){// 判断session是否存在// if (Session::has('user')) { //设置的时候就设置了res,不要来读的时候就干个user在上面if (Session::has('res')) { // 如果session存在,继续执行后续请求return $next($request);} else {// 如果session不存在,重定向到登录页return redirect('../Index/index');}}
}
模型类,在这个案例中我们定义了两个模型类
一个是User模型类,就是管理员数据,另一个是UserList类就是展示在页面上的数据,我们增删改查需要操作的数据
User模型
<?php
namespace app\model;use think\Model;class User extends Model{protected $name = 'user';protected $pk = 'id';
}
UserList模型
<?php
namespace app\model;
use think\Model;class UserList extends Model{protected $name = 'user_list';protected $pk = 'id';
}
这个案例并没有用到路由模块,有需要用路由的自己去配置即可,router/app.php中
数据库
数据库就两个表
user和user_list
使用tp操作数据库前请先确保配置了数据库连接,开发环境跟目录下.env文件
生产环境config/database.php如果不知道是开发环境还是生产环境两个都改一下
表的结构

完结!
相关文章:
thinkphp6结合layui增删改查综合案列
文章目录 技术栈实现代码实现数据库 本案例适合新手,特别是杠刚入门thinkphp和layui,但又不是特别熟悉这类 主要实现登录退出功能,用户模块的增删改查功能,分页功能是layui表单自带功能 效果图 左侧的菜单栏我没有写对应的页面&am…...
PostgreSQL数据库以任意时间间隔聚合查询group by
文章目录 业务场景以固定时间(年/月/日/时/分/秒)聚合to_char聚合date_trunc聚合 以任意时间聚合date_bin聚合实际应用 业务场景 我们做的是交通信控平台,需要根据实时采集到的交通大数据,计算出一些指标,存储到数据库…...
sql注入(二)盲注,二次注入,宽字节注入
目录 目录 一、布尔盲注 1.判断库名的长度 2.判断数据库名 2.1判断数据库名首字符 2.2 判断数据库名的其余字符 二、时间盲注: 1.判断库名的长度 2.判断库名: 3.判断表名payload: 4.爆出列名 5.爆数据 三、二次注入 1.原理&#…...
Linux 基础操作
Linux学习教程,Linux入门教程(超详细) chown (change owner) : 修改所属用户与组。chmod (change mode) : 修改用户的权限。 要查看文件或目录的属性,可以使用ls命令,加上-l选项。例如ÿ…...
2.4 等比数列
学习步骤: 如果我要学习等比数列,我会按照以下步骤进行学习: 定义和性质:首先了解等比数列的定义和性质,包括公比、首项、通项公式、求和公式等。 例题练习:通过练习一些简单的例题来理解等比数列的概念和…...
2022年新能源汽车专题讲座
2022年新能源汽车专题讲座 单选题(共5题,每题6分) 1、《中华人民共和国数据安全法》自()起施行。 正确答案:C、2021年9月1日 2、典型的智能汽车结构主要分为()个层次。 正确答案…...
Git操作远程仓库
远程仓库 码云 https://gitee.com/ 是国内的一个代码托管平台,由于服务器在国内,所以相比于GitHub,码云速度会更快 码云使用流程 注册账号----登录码云-----点击新建仓库----记得保存地址 GitHub https://github.com/ 是一个面向开源…...
制造策略 ETO、MTO、ATO、MTS
ETO 按交货周期跨度从长到短来讲,首先就是 ETO,Engineer To Order – 面向订单设计、定制生产或特殊生产。 就是客户给的订单,你要生产的话,你之前的原产品改动很大,或者基本上用不上,要完全按照客户的要求…...
Git(六):基本命令(3):储藏、标签、拉取、子模块
目录 17、stash 储藏 17.2 描述 17.3 基本用法 18、tag 标签 18.1 描述 18.2 基本用法 19、fetch 获取 19.1 描述 19.2 基本用法 20、pull 整合 20.1 描述 20.2 基本用法 20.3 pull 与 fetch 的区别 21、push 更新推送 21.1 描述 21.2 基本用法 22、remote 管…...
7.0、Java继承与多态 - 多态的特性
7.0、Java继承与多态 - 多态的特性 面向对象的三大特征:封装性、继承性、多态性; extends继承 或者 implements实现,是多态性的前提; 用学生类创建一个对象 - 小明,他是一个 学生(学生形态)&…...
将系统从机械硬盘迁移至固态硬盘上
1、使用DiskGenius软件、分区助手或者傲梅分区助手进行系统迁移 参考: 系统迁移 - DiskGenius 分区助手专业版如何迁移系统到固态硬盘-迁移系统到固态硬盘的方法_华军软件园 (onlinedown.net) 无需重装,轻松将系统迁移到固态硬盘! (disktool.cn) 注…...
《Netty》从零开始学netty源码(五十一)之PoolArena的内存释放与扩容
目录 释放空间free()destroyChunk()freeChunk() 扩容reallocate()memoryCopy() 释放空间free() 当chunk使用完毕后需要释放,如果是池化chunk则需要放回池中供下次循环利用,如果是非池化的则直接释放对应的物理空间。 下面继续分析释放具体物理空间的des…...
Android Input系统事件分发分析
“本文基于Android13源码,分析Input系统中,事件分发的实现原理“ 整个事件分发到事件的确认过程很长,如果读者只是想大概了解一下,可以直接看末尾总结部分的流程图。 1. 前言 在文章之前,有必要提一下InputReader。其…...
Linux-基本指令2
文章目录 touch(新建一个文件)whoami(查看当前用户名)概念:1.你是如何看待指令的?2.我们在执行指令之前,我们应该先做什么? 概念:/tree . (树状显示文件夹和文件)rmdir && rmrmdirrm ctrl c通配符…...
辨析 项目范围核查、WBS核查
项目范围核查、WBS核查辨析 项目范围核查 项目目标是否完善和准确指标是否可靠和有效约束和限制条件是否真实和符合实际重要假设前提是否合理风险是否可以接受成功把握是否很大范围定义是否能够保证上述目标的实现范围能够给出的效益是否高于成本范围定义是否需要进一步进行辅…...
跳跃游戏类题目 总结篇
一.跳跃游戏类题目简单介绍 跳跃游戏是一种典型的算法题目,经常是给定一数组arr,从数组的某一位置i出发,根据一定的跳跃规则,比如从i位置能跳arr[i]步,或者小于arr[i]步,或者固定步数,直到到达某…...
Ubuntu20.04 交叉编译Paddle-OCR
第一步:交叉编译Paddle-Lite 参考链接:https://blog.csdn.net/sz76211822/article/details/130466597?spm1001.2014.3001.5501 第二步:交叉编译opencv4.x 参考链接:https://blog.csdn.net/sz76211822/article/details/13046168…...
Java 基础进阶篇(四)—— 权限修饰符、final 关键字与枚举
文章目录 一、权限修饰符二、final 关键字2.1 final 作用2.2 final 修饰变量举例2.3 常量 三、枚举3.1 枚举的格式3.2 枚举的特征3.3 枚举的应用 一、权限修饰符 权限修饰符 用于约束成员变量、构造器、方法等的访问范围。 权限修饰符: 有四种作用范围由小到大 (p…...
Linux命令集(Linux文件管理命令--touch指令篇)
Linux命令集(Linux文件管理命令--touch指令篇) Linux文件管理命令集(touch指令篇)6. touch(touch)1. 创建名为 file1 的空文件2. 创建名为 file1 和名为 file2 的多个文件3. 创建名为 file1 的文件并将访问时间设置为特定日期4. 创…...
软件工程学习教程大纲
软件工程学习教程大纲 第一章:软件工程概述 1.1 软件工程的定义和作用 软件工程的发展历程和趋势 软件工程的应用领域和特点 1.2 软件开发生命周期 软件开发生命周期的定义和阶段 软件开发生命周期的模型和方法 1.3 软件工程方法和工具 软件工程方法和工具…...
理解 MCP 工作流:使用 Ollama 和 LangChain 构建本地 MCP 客户端
🌟 什么是 MCP? 模型控制协议 (MCP) 是一种创新的协议,旨在无缝连接 AI 模型与应用程序。 MCP 是一个开源协议,它标准化了我们的 LLM 应用程序连接所需工具和数据源并与之协作的方式。 可以把它想象成你的 AI 模型 和想要使用它…...
MySQL 8.0 OCP 英文题库解析(十三)
Oracle 为庆祝 MySQL 30 周年,截止到 2025.07.31 之前。所有人均可以免费考取原价245美元的MySQL OCP 认证。 从今天开始,将英文题库免费公布出来,并进行解析,帮助大家在一个月之内轻松通过OCP认证。 本期公布试题111~120 试题1…...
Web 架构之 CDN 加速原理与落地实践
文章目录 一、思维导图二、正文内容(一)CDN 基础概念1. 定义2. 组成部分 (二)CDN 加速原理1. 请求路由2. 内容缓存3. 内容更新 (三)CDN 落地实践1. 选择 CDN 服务商2. 配置 CDN3. 集成到 Web 架构 …...
USB Over IP专用硬件的5个特点
USB over IP技术通过将USB协议数据封装在标准TCP/IP网络数据包中,从根本上改变了USB连接。这允许客户端通过局域网或广域网远程访问和控制物理连接到服务器的USB设备(如专用硬件设备),从而消除了直接物理连接的需要。USB over IP的…...
MySQL 部分重点知识篇
一、数据库对象 1. 主键 定义 :主键是用于唯一标识表中每一行记录的字段或字段组合。它具有唯一性和非空性特点。 作用 :确保数据的完整性,便于数据的查询和管理。 示例 :在学生信息表中,学号可以作为主键ÿ…...
pikachu靶场通关笔记19 SQL注入02-字符型注入(GET)
目录 一、SQL注入 二、字符型SQL注入 三、字符型注入与数字型注入 四、源码分析 五、渗透实战 1、渗透准备 2、SQL注入探测 (1)输入单引号 (2)万能注入语句 3、获取回显列orderby 4、获取数据库名database 5、获取表名…...
Vue 模板语句的数据来源
🧩 Vue 模板语句的数据来源:全方位解析 Vue 模板(<template> 部分)中的表达式、指令绑定(如 v-bind, v-on)和插值({{ }})都在一个特定的作用域内求值。这个作用域由当前 组件…...
基于 HTTP 的单向流式通信协议SSE详解
SSE(Server-Sent Events)详解 🧠 什么是 SSE? SSE(Server-Sent Events) 是 HTML5 标准中定义的一种通信机制,它允许服务器主动将事件推送给客户端(浏览器)。与传统的 H…...
C#中用于控制自定义特性(Attribute)
我们来详细解释一下 [AttributeUsage(AttributeTargets.Class, AllowMultiple false, Inherited false)] 这个 C# 属性。 在 C# 中,Attribute(特性)是一种用于向程序元素(如类、方法、属性等)添加元数据的机制。Attr…...
构建Docker镜像的Dockerfile文件详解
文章目录 前言Dockerfile 案例docker build1. 基本构建2. 指定 Dockerfile 路径3. 设置构建时变量4. 不使用缓存5. 删除中间容器6. 拉取最新基础镜像7. 静默输出完整示例 docker runDockerFile 入门syntax指定构造器FROM基础镜像RUN命令注释COPY复制ENV设置环境变量EXPOSE暴露端…...
