SpringMVC——第6章:RESTFul编程风格
一、RESTFul编程风格
1.RESTFul是什么
RESTFul是WEB服务接口
的一种设计风格。 RESTFul定义了一组约束条件和规范,可以让WEB服务接口
更加简洁、易于理解、易于扩展、安全可靠。
RESTFul对一个WEB服务接口
都规定了哪些东西?
对请求的URL格式有约束和规范
对HTTP的请求方式有约束和规范
对请求和响应的数据格式有约束和规范
对HTTP状态码有约束和规范
等 ......
REST对请求方式的约束是这样的:
查询必须发送GET请求
新增必须发送POST请求
修改必须发送PUT请求
删除必须发送DELETE请求
REST对URL的约束是这样的:
传统的URL:get请求,/springmvc/getUserById?id=1
REST风格的URL:get请求,/springmvc/user/1
传统的URL:get请求,/springmvc/deleteUserById?id=1
REST风格的URL:delete请求, /springmvc/user/1
RESTFul对URL的约束和规范的核心是:通过采用**不同的请求方式**
+ **URL**
来确定WEB服务中的资源。
RESTful 的英文全称是 Representational State Transfer(表述性状态转移)。简称REST。
表述性(Representational)是:URI + 请求方式。
状态(State)是:服务器端的数据。
转移(Transfer)是:变化。
表述性状态转移是指:通过 URI + 请求方式 来控制服务器端数据的变化。
2.RESTFul风格与传统方式对比
传统的 URL 与 RESTful URL 的区别是传统的 URL 是基于方法名进行资源访问和操作,而 RESTful URL 是基于资源的结构和状态进行操作的。下面是一张表格,展示两者之间的具体区别:
传统的 URL | RESTful URL |
---|---|
GET /getUserById?id=1 | GET /user/1 |
GET /getAllUser | GET /user |
POST /addUser | POST /user |
POST /modifyUser | PUT /user |
GET /deleteUserById?id=1 | DELETE /user/1 |
从上表中我们可以看出,传统的URL是基于动作的,而 RESTful URL 是基于资源和状态的,因此 RESTful URL 更加清晰和易于理解,这也是 REST 架构风格被广泛使用的主要原因之一。
3.RESTFul方式演示查询
RESTFul规范中规定,如果要查询数据,需要发送GET请求。
根据id查询和查询所有
测试:
4.RESTFul方式演示增加
RESTFul规范中规定,如果要进行保存操作,需要发送POST请求。
新增一个用户类
新增表单
测试:
5.RESTFul方式演示修改
RESTful编程风格中要求,修改的时候,必须提交PUT请求,怎么提交PUT请求呢?第一步:要想发送PUT请求,首先你必须是一个POST请求。(POST请求是大前提)第二步:在POST请求的表单中添加隐藏域:<!--隐藏域--><input type="hidden" name="_method" value="put">强调:name必须是 _method,value必须是put/PUT。如果你要发送delete请求的话,value写delete即可。第三步:添加一个过滤器<!--添加一个过滤器,这个过滤器是springmvc提前写好的,直接用就行了,这个过滤器可以帮助你将请求POST转换成PUT请求/DELETE请求--><filter><filter-name>hiddenHttpMethodFilter</filter-name><filter-class>org.springframework.web.filter.HiddenHttpMethodFilter</filter-class></filter><filter-mapping><filter-name>hiddenHttpMethodFilter</filter-name><url-pattern>/*</url-pattern></filter-mapping>
RESTFul规范中规定,如果要进行保存操作,需要发送PUT请求。
如何发送PUT请求?
第一步:首先你必须是一个POST请求。
第二步:在发送POST请求的时候,提交这样的数据:**_method=PUT**
第三步:在web.xml文件配置SpringMVC提供的过滤器:HiddenHttpMethodFilter
实践一下:
在web.xml配置
<!--隐藏的HTTP请求方式过滤器-->
<filter><filter-name>hiddenHttpMethodFilter</filter-name><filter-class>org.springframework.web.filter.HiddenHttpMethodFilter</filter-class>
</filter>
<filter-mapping><filter-name>hiddenHttpMethodFilter</filter-name><url-pattern>/*</url-pattern>
</filter-mapping>
测试:
6.HiddenHttpMethodFilter
HiddenHttpMethodFilter是Spring MVC框架提供的,专门用于RESTFul编程风格。 实现原理可以通过源码查看:
通过源码可以看到,if语句中,首先判断是否为POST请求,如果是POST请求,调用request.getParameter(this.methodParam)
。
可以看到this.methodParam
是_method
,这样就要求我们在提交请求方式的时候必须采用这个格式:_method=put
。获取到请求方式之后,调用了toUpperCase转换成大写了。因此前端页面中小写的put或者大写的PUT都是可以的。if语句中嵌套的if语句说的是,只有请求方式是 PUT,DELETE,PATCH的时候会创建HttpMethodRequestWrapper对象。而HttpMethodRequestWrapper对象的构造方法是这样的:
这样method就从POST变成了:PUT/DELETE/PATCH。
重点注意事项:CharacterEncodingFilter和HiddenHttpMethodFilter的顺序 细心的同学应该注意到了,在HiddenHttpMethodFilter源码中有这样一行代码:
大家是否还记得,字符编码过滤器执行之前不能调用 request.getParameter方法,如果提前调用了,乱码问题就无法解决了。因为request.setCharacterEncoding()方法的执行必须在所有request.getParameter()方法之前执行。因此这两个过滤器就有先后顺序的要求,在web.xml文件中,应该先配置CharacterEncodingFilter,然后再配置HiddenHttpMethodFilter。
7.RESTFul方式演示删除
测试:
二、使用RESTFul实现用户管理系统
1.·静态页面准备
文件包括:user.css、user_index.html、user_list.html、user_add.html、user_edit.html。代码如下:
user.css
.header {background-color: #f2f2f2;padding: 20px;text-align: center;
}ul {list-style-type: none;margin: 0;padding: 0;overflow: hidden;background-color: #333;
}li {float: left;
}li a {display: block;color: white;text-align: center;padding: 14px 16px;text-decoration: none;
}li a:hover:not(.active) {background-color: #111;
}.active {background-color: #4CAF50;
}form {width: 50%;margin: 0 auto;padding: 20px;border: 1px solid #ddd;border-radius: 4px;
}label {display: block;margin-bottom: 8px;
}input[type="text"], input[type="email"], select {width: 100%;padding: 6px 10px;margin: 8px 0;box-sizing: border-box;border: 1px solid #555;border-radius: 4px;font-size: 16px;
}button[type="submit"] {padding: 10px;background-color: #4CAF50;color: #fff;border: none;border-radius: 4px;cursor: pointer;
}button[type="submit"]:hover {background-color: #3e8e41;
}table {border-collapse: collapse;width: 100%;
}th, td {border: 1px solid #ddd;padding: 8px;text-align: left;
}th {background-color: #f2f2f2;
}tr:nth-child(even) {background-color: #f2f2f2;
}.header {background-color: #f2f2f2;padding: 20px;text-align: center;
}a {text-decoration: none;color: #333;
}.add-button {margin-bottom: 20px;padding: 10px;background-color: #4CAF50;color: #fff;border: none;border-radius: 4px;cursor: pointer;
}.add-button:hover {background-color: #3e8e41;
}
user_index.html
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>用户管理系统</title><link rel="stylesheet" href="user.css" type="text/css"></link>
</head>
<body><div class="header"><h1>用户管理系统</h1></div><ul><li><a class="active" href="user_list.html">用户列表</a></li></ul>
</body>
</html>
user_list.html
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>用户列表</title><link rel="stylesheet" href="user.css" type="text/css"></link>
</head>
<body><div class="header"><h1>用户列表</h1></div><div class="add-button-wrapper"><a class="add-button" href="user_add.html">新增用户</a></div><table><thead><tr><th>编号</th><th>用户名</th><th>性别</th><th>邮箱</th><th>操作</th></tr></thead><tbody><tr><td>1</td><td>张三</td><td>男</td><td>zhangsan@powernode.com</td><td>修改删除</td></tr><tr><td>2</td><td>李四</td><td>女</td><td>lisi@powernode.com</td><td>修改删除</td></tr></tbody></table>
</body>
</html>
user_add.html
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>新增用户</title><link rel="stylesheet" href="user.css" type="text/css"></link>
</head>
<body><h1>新增用户</h1><form><label>用户名:</label><input type="text" name="username" required><label>性别:</label><select name="gender" required><option value="">-- 请选择 --</option><option value="1">男</option><option value="0">女</option></select><label>邮箱:</label><input type="email" name="email" required><button type="submit">保存</button></form>
</body>
</html>
user_edit.html
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>修改用户</title><link rel="stylesheet" href="user.css" type="text/css"></link>
</head>
<body><h1>修改用户</h1><form><label>用户名:</label><input type="text" name="username" value="张三" required><label>性别:</label><select name="gender" required><option value="">-- 请选择 --</option><option value="1" selected>男</option><option value="0">女</option></select><label>邮箱:</label><input type="email" name="email" value="zhangsan@powernode.com" required><button type="submit">修改</button></form>
</body>
</html>
代码有两处需要修改:
部署,启动服务器,测试:
2.实现用户列表
修改user_index.html中的超链接:
编写bean:User
package org.example1.bean;public class User {/*** 用户编号*/private Long id;/*** 用户名*/private String username;/*** 性别* 1表示男* 0表示女*/private Integer sex;/*** 邮箱*/private String email;public User() {}public User(Long id, String username, Integer sex, String email) {this.id = id;this.username = username;this.sex = sex;this.email = email;}@Overridepublic String toString() {return "User{" +"id=" + id +", username='" + username + '\'' +", sex=" + sex +", email='" + email + '\'' +'}';}public Long getId() {return id;}public void setId(Long id) {this.id = id;}public String getUsername() {return username;}public void setUsername(String username) {this.username = username;}public Integer getSex() {return sex;}public void setSex(Integer sex) {this.sex = sex;}public String getEmail() {return email;}public void setEmail(String email) {this.email = email;}
}
编写UserDao,提供selectAll方法:
package org.example1.dao;import org.example1.bean.User;
import org.springframework.stereotype.Repository;import java.util.ArrayList;
import java.util.List;@Repository
public class UserDao {private static List<User> users = new ArrayList<>();static {// 类加载是初始化数据// 创建User对象User user1 = new User(1001L,"张三", 1, "zhangsan@powernode.com");User user2 = new User(1002L,"孙悟空", 1, "wukong@powernode.com");User user3 = new User(1003L,"猪八戒", 1, "bajie@powernode.com");User user4 = new User(1004L,"白骨精", 0, "bgj@powernode.com");User user5 = new User(1005L,"武松", 1, "ws@powernode.com");// 将User对象存储到List集合中users.add(user1);users.add(user2);users.add(user3);users.add(user4);users.add(user5);}/*** 查询所有的用户信息* @return 用户列表List集合*/public List<User> selectAll(){return users;}}
编写控制器UserController:
package org.example1.controller;import org.example1.bean.User;
import org.example1.dao.UserDao;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;import java.util.List;@Controller
public class UserController {@Autowiredprivate UserDao userDao;@RequestMapping(value = "/user", method = RequestMethod.GET)public String list(Model model){// 查询数据库,获取用户列表List集合List<User> users = userDao.selectAll();// 将用户列表存储到request域当中model.addAttribute("users", users);// 转发到视图return "user_list";}}
将user_list.html拷贝到thymeleaf目录下,并进行代码修改,显示用户列表:
<!DOCTYPE html>
<html lang="en" xmlns:th="http://www.thymeleaf.org">
<head><meta charset="UTF-8"><title>用户列表</title><link rel="stylesheet" th:href="@{/static/user.css}" type="text/css"></link>
</head>
<body><div class="header"><h1>用户列表</h1></div><div class="add-button-wrapper"><a class="add-button" href="user_add.html">新增用户</a></div><table><thead><tr><th>编号</th><th>用户名</th><th>性别</th><th>邮箱</th><th>操作</th></tr></thead><tbody><tr th:each="user : ${users}"><td th:text="${user.id}"></td><td th:text="${user.name}"></td><td th:text="${user.gender == 1 ? '男' : '女'}"></td><td th:text="${user.email}"></td><td><a href="">修改</a><a href="">删除</a></td></tr></tbody></table>
</body>
</html>
测试结果:
3.实现新增功能
跳转到新增页面
在用户列表页面,修改新增用户
的超链接:
将user_add.html拷贝到thymeleaf目录下,并进行代码修改如下:
<!DOCTYPE html>
<html lang="en" xmlns:th="http:www.thymeleaf.org">
<head><meta charset="UTF-8"><title>新增用户</title><link rel="stylesheet" th:href="@{/static/user.css}" type="text/css"></link>
</head>
<body><h1>新增用户</h1><form><label>用户名:</label><input type="text" name="username" required><label>性别:</label><select name="gender" required><option value="">-- 请选择 --</option><option value="1">男</option><option value="0">女</option></select><label>邮箱:</label><input type="email" name="email" required><button type="submit">保存</button></form>
</body>
</html>
在springmvc.xml文件中配置视图控制器映射
:
<mvc:view-controller path="/toSave" view-name="user_add"/>
启动服务器测试:
实现新增功能
前端页面发送POST请求,提交表单,user_add.html代码如下:
<!DOCTYPE html>
<html lang="en" xmlns:th="http:www.thymeleaf.org">
<head><meta charset="UTF-8"><title>新增用户</title><link rel="stylesheet" th:href="@{/static/user.css}" type="text/css"></link>
</head>
<body><h1>新增用户</h1><form th:action="@{/user}" method="post"><label>用户名:</label><input type="text" name="name" required><label>性别:</label><select name="gender" required><option value="">-- 请选择 --</option><option value="1">男</option><option value="0">女</option></select><label>邮箱:</label><input type="email" name="email" required><button type="submit">保存</button></form>
</body>
</html>
编写控制器UserController:
注意:保存成功后,采用重定向的方式跳转到用户列表。
编写UserDao:
注意:单独写了一个方法生成id,内部使用了Stream API,不会这块内容的可以看老杜最新发布的2024版JavaSE。
4.跳转到修改页面
修改user_list.html中修改
超链接:
<a th:href="@{'/user/' + ${user.id}}">修改</a>
编写Controller:
@GetMapping("/user/{id}")
public String toUpdate(@PathVariable("id") Long id, Model model){// 根据id查询用户信息User user = userDao.selectById(id);// 将对象存储到request域model.addAttribute("user", user);// 跳转视图return "user_edit";
}
编写UserDao:
public User selectById(Long id){return users.stream().filter(user -> user.getId().equals(id)).findFirst().get();
}
将user_edit.html拷贝thymeleaf目录下,并修改代码如下:
<!DOCTYPE html>
<html lang="en" xmlns:th="http://www.thymeleaf.org">
<head><meta charset="UTF-8"><title>修改用户</title><link rel="stylesheet" th:href="@{/static/user.css}" type="text/css"></link>
</head>
<body><h1>修改用户</h1><form><label>用户名:</label><input type="text" name="username" th:value="${user.name}" required><label>性别:</label><select name="gender" required><option value="">-- 请选择 --</option><option value="1" th:field="${user.gender}">男</option><option value="0" th:field="${user.gender}">女</option></select><label>邮箱:</label><input type="email" name="email" th:value="${user.email}" required><button type="submit">修改</button></form>
</body>
</html>
启动服务器测试:
5.实现修改功能
将user_edit.html页面中的form表单修改一下,添加action,添加method,隐藏域的方式提交请求方式put,隐藏域的方式提交id:
<form th:action="@{/user}" method="post"><!--隐藏域的方式设置请求方式为put请求--><input type="hidden" name="_method" value="put"><!--隐藏域的方式提交id--><input type="hidden" name="id" th:value="${user.id}"><label>用户名:</label><input type="text" name="name" th:value="${user.name}" required><label>性别:</label><select name="gender" required><option value="">-- 请选择 --</option><option value="1" th:field="${user.gender}">男</option><option value="0" th:field="${user.gender}">女</option></select><label>邮箱:</label><input type="email" name="email" th:value="${user.email}" required><button type="submit">修改</button>
</form>
编写Controller:
@PutMapping("/user")
public String modify(User user){// 更新数据userDao.update(user);// 重定向return "redirect:/user";
}
编写UserDao:
public void update(User user){for (int i = 0; i < users.size(); i++) {if(user.getId().equals(users.get(i).getId())){users.set(i, user);break;}}
}
启动服务器测试:
6.实现删除功能
删除应该发送DELETE请求,要模拟DELETE请求,就需要使用表单方式提交。因此我们点击删除
超链接时需要采用表单方式提交。 在user_list.html页面添加form表单,并且点击超链接时应该提交表单,代码如下:
<!DOCTYPE html>
<html lang="en" xmlns:th="http://www.thymeleaf.org">
<head><meta charset="UTF-8"><title>用户列表</title><link rel="stylesheet" th:href="@{/static/user.css}" type="text/css"></link>
</head>
<body><div class="header"><h1>用户列表</h1></div><div class="add-button-wrapper"><a class="add-button" th:href="@{/toSave}">新增用户</a></div><table><thead><tr><th>编号</th><th>用户名</th><th>性别</th><th>邮箱</th><th>操作</th></tr></thead><tbody><tr th:each="user : ${users}"><td th:text="${user.id}"></td><td th:text="${user.name}"></td><td th:text="${user.gender == 1 ? '男' : '女'}"></td><td th:text="${user.email}"></td><td><a th:href="@{'/user/' + ${user.id}}">修改</a><!--为删除提供一个鼠标单击事件--><a th:href="@{'/user/' + ${user.id}}" onclick="del(event)">删除</a></td></tr></tbody></table><!--为删除操作准备一个form表单,点击删除时提交form表单--><div style="display: none"><form method="post" id="delForm"><input type="hidden" name="_method" value="delete"/></form></div><script>function del(event){// 获取表单let delForm = document.getElementById("delForm");// 设置表单actiondelForm.action = event.target.href;if(window.confirm("您确定要删除吗?")){// 提交表单delForm.submit();}// 阻止超链接默认行为event.preventDefault();}</script>
</body>
</html>
编写Controller:
@DeleteMapping("/user/{id}")
public String del(@PathVariable("id") Long id){// 删除userDao.deleteById(id);// 重定向return "redirect:/user";
}
编写UserDao:
public void deleteById(Long id){for (int i = 0; i < users.size(); i++) {if(id.equals(users.get(i).getId())){users.remove(i);break;}}
}
相关文章:
SpringMVC——第6章:RESTFul编程风格
一、RESTFul编程风格 1.RESTFul是什么 RESTFul是WEB服务接口的一种设计风格。 RESTFul定义了一组约束条件和规范,可以让WEB服务接口更加简洁、易于理解、易于扩展、安全可靠。 RESTFul对一个WEB服务接口都规定了哪些东西? 对请求的URL格式有约束和规范…...
深度解析:从 GPT-4o“谄媚”到 Deepseek“物理腔”,透视大模型行为模式的底层逻辑与挑战
深度解析:从 GPT-4o“谄媚”到 AI“物理腔”,透视大模型行为模式的底层逻辑与挑战 标签:人工智能, GPT-4o, 大语言模型, AI伦理, 人机交互, 技术思考 大家好!最近AI圈最火的“瓜”之一,莫过于OpenAI的GPT-4o模型在一…...
2025 年最新树莓派 Pico 连接 OLED 显示字模汉字详细教程
OLED 概述 OLED(Organic Light-Emitting Diode,有机发光二极管)是一种基于有机材料的发光技术,通过电流驱动有机薄膜发光,具有自发光、高对比度、柔性可弯曲等特点。 4 针脚 OLED 硬件电路如图所示,GND 接…...
【Ubuntu 安装Docker CE-Jenkins】
安装Docker CE(Ubuntu) Install | Docker Docs官网 使用apt仓库安装 DNS配置(可选) #手动替换 sudo vim /etc/systemd/resolved.conf #典型配置如下 [Resolve] DNS8.8.8.8 DNS114.114.114.114 FallbackDNS1.1.1.1 # 备用 DNS#sed替换 sudo sed -i /^#DNS/ {s/#DNS/DNS8.8.8…...
知识图谱 + 大语言模型:打造更聪明、更可靠的AI大脑 —— 探索 GraphRAG 中文优化与可视化实践
大语言模型(LLMs)无疑是近年来人工智能领域最耀眼的明星。它们强大的自然语言理解和生成能力,在文本创作、代码生成、对话交互等众多领域展现了惊人的潜力。然而,当前的 LLMs 并非完美无缺,它们常常面临着“幻觉”&…...
三、【LLaMA-Factory实战】模型微调进阶:从LoRA到MoE的技术突破与工程实践
一、引言 在大模型微调领域,选择合适的训练策略直接决定了效率与效果的平衡。LLaMA-Factory深度整合了参数高效微调(PEFT)、全量微调、混合专家模型(MoE)等12种训练策略,支持从消费级GPU到多卡集群的全场景…...
Photo-SLAM论文理解、环境搭建、代码理解与实测效果
前言:第一个解耦式Photo-SLAM,亮点和效果。 参考:https://zhuanlan.zhihu.com/p/715311759 全网最细PhotoSLAM的conda环境配置教程,拒绝环境污染!!-CSDN博客 1. 环境搭建 硬件:RTX 4090D wi…...
解决pycharm检测不到已经装好的conda的pytorch环境
问题 1.找装anaconda的位置(我装到了py-anacon下) 2.找到下图中的conda.bat 3.pycharm社区版右下角,添加新解释器 4.选conda环境,选择2.中conda.bat的位置,加载环境,使用现有环境,可以看到有选…...
【计算机视觉】3d人脸重建:3DDFA_V2:实时高精度3D人脸重建与密集对齐技术指南
3d人脸重建:3DDFA_V2:实时高精度3D人脸重建与密集对齐技术指南 一、项目概述与技术背景1.1 3DDFA_V2核心价值1.2 技术演进路线1.3 核心技术指标 二、环境配置与模型部署2.1 硬件要求2.2 软件安装基础环境搭建关键组件安装 2.3 模型下载 三、核心算法原理…...
谈判模拟器 - Gemini 2.5 商业优化版
核心目标: 基于深厚的理论知识、丰富的实战经验和前沿的技术洞察,结合麦肯锡领先的谈判策略框架,为用户提供全面、深入、可操作的商业谈判策略指导和建议,助力其在复杂商业环境中达成最优谈判结果,并实现商业价值最大化…...
深度学习系统学习系列【4】之反向传播(BP)四个基本公式推导
文章目录 补充知识:∇ 和 ⊙ 运算符详解∇ (nabla) 运算符⊙ (圆圈点) 运算符 反向传播基本公式计算图和基本定义BP1:输出层误差推导BP1公式的重要性实际例子BP2第 l l l层误差推导BP3 :损失函数关于偏置(b)偏导的推导BP4: 损失函…...
算法每日一题 | 入门-顺序结构-上学迟到
上学迟到 题目描述 学校和 yyy 的家之间的距离为 s 米,而 yyy 以 v 米每分钟的速度匀速走向学校。 在上学的路上,yyy 还要额外花费 10 分钟的时间进行垃圾分类。 学校要求必须在上午 8:00 到达,请计算在不迟到的前提下,yyy 最…...
开源库测试
yolov10 https://github.com/THU-MIG/yolov10 conda create -n yolov10 python3.9 conda activate yolov10 pip install -r requirements.txt pip install -e .报错 找不到对应版本 Could not find a version that satisfies the requirement gradio4.31.5 (from versions:…...
因为gromacs必须安装cuda(系统自带的NVIDIA驱动不行),这里介绍下如何安装cuda
1. 安装步骤 查看是否安装了cuda # 法1 cat /usr/local/cuda/version.txt # 法2 nvcc --version 若没有安装,则查看是否有N卡驱动,若无N卡驱动,则到软件与更新 -> 附加驱动中安装驱动 查看N卡驱动支持的cuda版本 nvidia-smi 如下…...
ABC 404
1.C 题: 1.思路: NM&每个点读数为2,但图中有可能出现多环,需要判断所有点是否都在同一连通块上,有俩种解法:搜索,循环 2.代码(循环做法) #include<bits/stdc.h&g…...
机器学习朴素贝叶斯算法
1.朴素贝叶斯算法 1.1基本概念 其分类原理是利用贝叶斯公式根据某特征的先验概率计算出其后验概率,然后选择具有最大后验概率作为该特征所属的类。之所以称之为“朴素”,是因为贝叶斯分类只做最原始、最简单的假设:所有的特征之间是相对独立…...
Linux:深入理解数据链路层
实际上一台主机中,报文并没有通过网络层直接发送出去,而是交给了自己的下一层协议——数据链路层!! 一、理解数据链路层 网络层交付给链路层之前,会先做决策再行动(会先查一下路由表,看看目标网…...
健康养生:从生活点滴启航
养生并非遥不可及的高深学问,只需把握生活中的细微之处,就能为健康保驾护航。 清晨睁眼,先在床上做简单的搓脸动作,从下巴到额头轻柔按摩,促进面部血液循环,唤醒肌肤活力。随后空腹喝一杯温水,可…...
【向量数据库】用披萨点餐解释向量数据库:一个美味的技术类比
文章目录 前言场景设定:披萨特征向量化顾客到来:生成查询向量相似度计算实战1. 欧氏距离计算(值越小越相似)2. 余弦相似度计算(值越大越相似) 关键发现:度量选择影响结果现实启示结语 前言 想象…...
CloudCompare 中 ccDrawableObject
CloudCompare 中 ccDrawableObject 类的主要内容与使用 1. ccDrawableObject 概述 在 CloudCompare 中,ccDrawableObject 是一个基类,主要用于管理 3D 可绘制对象 的显示属性,如颜色、可见性、LOD(层次细节)、光照等…...
【Linux】进程控制
🌟🌟作者主页:ephemerals__ 🌟🌟所属专栏:Linux 目录 前言 一、什么是进程控制 二、进程创建 三、进程终止(进程退出) 退出码 main函数返回 _exit() exit() 测试 四、进…...
设计模式-基础概念学习总结(继承、多态、虚方法、方法重写)
概念使用例子的方式介绍(继承,多态,虚方法,方法重写),实现代码python 1. 继承(Inheritance) 概念:子类继承父类的属性和方法,可以直接复用父类的代码&#…...
分析rand()和srand()函数的功能
rand()和srand()函数原型: int rand(void) 返回一个范围在 0 到 RAND_MAX 之间的伪随机数。 void srand(unsigned int seed)用来给rand() 设置随机数发生器,随机数发生器输出不同的数值,rand() 就会生成不同的随机数 1)、在“D:\Keil_v5\AR…...
架构师如何构建个人IP:职业规划与业务战略的双重提升
在数字化时代,软件架构师的角色已从单纯的技术专家转变为兼具技术领导力和业务影响力的复合型人才。如何构建个人IP,提升行业影响力,成为架构师职业发展的关键课题。本文从个人认知、业务战略、架构决策、产品思维四个维度,探讨架…...
CSS知识总结
一、CSS核心概念解析 1.1 选择器体系(重点) 基础选择器: /* ID选择器 */ #header { background: #333; }/* 类选择器 */ .btn-primary { color: white; }/* 属性选择器 */ input[type"text"] { border: 1px solid #ccc; } 组合…...
CRS 16 slot 设备硬件架构
目录 1. 核心组件 1.1 线路卡与物理接口模块 1.2 交换结构与容量 1.3 控制与管理 1.4 风扇与散热 1.5 电源与告警 2. 插槽编号与机箱布局 2.1 前侧(PLIM 面) 2.2 后侧(MSC 面) 2.3 插槽配对 1. 核心组件 1.1 线路卡与物…...
人工智能浪潮中Python的核心作用与重要地位
在人工智能(Artificial Intelligence,AI)蓬勃发展的时代,Python已然成为推动这一技术进步的关键编程语言。从复杂的机器学习算法实现,到前沿的深度学习模型构建,再到智能系统的部署,Python无处不…...
【了解】数字孪生网络(Digital Twin Network,DTN)
目录 一、为什么?二、是什么?三、什么架构?四、如何应用?参考 一、为什么? 一方面,网络负载不断增加,,网络规模持续扩大带来的网络复杂性,使得网络的运行和维护变得越来越复杂。另一…...
[C语言]第一章-初识
目录 一.引言 二.MinGW 下载与安装 1.什么是 MinGW 2.下载 MinGW 3.安装 MinGW 4.配置 MinGW 环境变量 三.VS Code 下载与安装 1.什么是 VS Code 2.下载 VS Code 3.安装 VS Code 4.汉化 5.安装扩展插件 C/C 截图 四.编写并运行 Hello World 程序 代码解释 运行…...
如何用git将项目上传到github
步骤 1.创建仓库 2.记下仓库的url 3.在本地初始化仓库 路径要在项目下 cd /path/to/your/vue-project git init 4.创建touch .gitignore文件 在项目根目录下创建 .gitignore 文件,用于指定 Git 忽略哪些文件或文件夹 5.添加和提交项目文件 将文件提交到版本控…...
C++入门(上)--《Hello C++ World!》(1)(C/C++)
文章目录 前言命名空间域命名空间的用法 C的输入和输出缺省参数函数重载auto关键字(C11)范围for 前言 C不是C# C兼容大部分C的东西,但不是完全(98%的样子,除非遇到了不兼容的,那就记一下,不然就认为自己在C里面写的那些可以写到C里…...
架构思维:构建高并发读服务_基于流量回放实现读服务的自动化测试回归方案
文章目录 引言一、升级读服务架构,为什么需要自动化测试?二、自动化回归测试系统:整体架构概览三、日志收集1. 拦截方式2. 存储与优化策略3. 架构进化 四、数据回放技术实现关键能力 五、差异对比对比方式灵活配置 六、三种回放模式详解1. 离…...
代码随想录第33天:动态规划6(完全背包基础)
一、完全平方数(Leetcode 279) 本题与“零钱兑换”基本一致。 1.确定dp数组以及下标的含义 dp[j]:和为j的完全平方数的最少数量为dp[j] 2.确定递推公式 dp[j] 可以由dp[j - i * i]推出, dp[j - i * i] 1 便可以凑成dp[j]。 …...
Android控件View、ImageView、WebView用法
一 控件清单 View、ImageView、WebView 二 控件UI代码 <?xml version="1.0" encoding="utf-8"?> <androidx.coordinatorlayout.widget.CoordinatorLayoutxmlns:android="http://schemas.android.com/apk/res/android"xmlns:app=&qu…...
关于浏览器页面自动化操作
Selenium 是一个用于自动化浏览器操作的强大框架,广泛应用于Web应用程序的测试自动化。它主要由以下几个核心组件组成: Selenium WebDriver: WebDriver 是 Selenium 的核心组件,它提供了一组API,允许开发者编写程序来…...
P5739 计算阶乘详解
此题目,对于会递归的很简单很简单,但作者是野人不会,只能是边刷边学,且题解比较有意思,所有我这次的重心不是题目,而是题解里面创作者展示的不一样的东西,先看题目 题目要求不用for循环…...
把Android设备变成“国标摄像头”:GB28181移动终端实战接入指南
把Android设备变成“国标摄像头”:GB28181移动终端实战接入指南 ——执法记录仪、巡检终端、布控球,如何通过大牛直播SDK直接挂到GB28181平台? 在过去,GB28181 通常用于固定摄像头、NVR等“设备端”。但在政务、安防、应急等行业…...
机器学习项目流程极简入门:从数据到部署的完整指南
前言 本文将通过一个简单案例(根据水果外观特征判断是否为橘子),逐步拆解机器学习项目的完整流程,帮助读者掌握从数据收集到模型部署的全流程方法论。 通常,一个完整的机器学习项目可以分为以下几个步骤: …...
PrivKV: Key-Value Data Collection with Local Differential Privacy论文阅读
文献阅读课需要制作ppt但是感觉选的这篇论文都是公式,决定做点动画直观展示一下。还没有完成会继续更新这个笔记 manim动画代码 需要下载ffmpeg下载latex https://docs.manim.org.cn/getting_started/installation.html ffmpeg下载教程 texlive官网 但是其实不需要…...
RViz(机器人可视化工具)的配置文件(moveitcpp)
1. Panels(面板设置) 面板是RViz界面中的各个功能区域,用于显示和操作不同的数据。 Displays(显示面板) Class: rviz_common/Displays 指定面板的类型,这里是显示面板。 Help Height: 78 帮助区域的高度…...
kotlin 01flow-StateFlow 完整教程
一 Android StateFlow 完整教程:从入门到实战 StateFlow 是 Kotlin 协程库中用于状态管理的响应式流,特别适合在 Android 应用开发中管理 UI 状态。本教程将带全面了解 StateFlow 的使用方法。 1. StateFlow 基础概念 1.1 什么是 StateFlow? StateF…...
OpenGl实战笔记(1)基于qt5.15.2+mingw64+opengl绘制三角形
一、实现效果 二、实现原理 (1)各函数作用与原理 initialize() 作用: 初始化 OpenGL 函数(initializeOpenGLFunctions()) 设置背景清除颜色为 rgba(0.2, 0.3, 0.4, 1.0)。 原理: initializeOpenGLFunctio…...
S100平台调试RS485/RS232
提供一个C语言的测试程序Demo #include <stdio.h> #include <stdlib.h> #include <string.h> #include <unistd.h>...
蓝桥杯 19. 植树
植树 题目描述 小明和朋友们一起去郊外植树,他们带了一些在实验室中精心研究出的小树苗。 一共有 n 个人,每个人挑选了一个适合植树的位置,一共 n 个位置。每人准备在自己的位置种下一棵树苗。 但他们遇到一个问题:有的树苗比…...
Spring Boot 中 @Bean 注解详解:从入门到实践
在 Spring Boot 开发中,Bean注解是一个非常重要且常用的注解,它能够帮助开发者轻松地将 Java 对象纳入 Spring 容器的管理之下,实现对象的依赖注入和生命周期管理。对于新手来说,理解并掌握Bean注解,是深入学习 Spring…...
git项目迁移,包括所有的提交记录和分支 gitlab迁移到gitblit
之前git都是全新项目上传,没有迁移过,因为迁移的话要考虑已有项目上的分支都要迁移过去,提交记录能迁移就好;分支如果按照全新项目上传的方式需要新git手动创建好老git已有分支,在手动一个一个克隆老项目分支代码依次提…...
前端面试每日三题 - Day 25
这是我为准备前端/全栈开发工程师面试整理的第25天每日三题练习,涵盖了: CSS中如何实现一个保持宽高比的自适应正方形元素Angular的变更检测(Change Detection)机制项目实战 - 设计一个微前端架构的前端应用。 ✅ 题目1ÿ…...
基于windows安装MySQL8.0.40
基于windows安装MySQL8.0.40 基于windows 安装 MySQL8.0.40,解压文件到D:\mysql-8.0.40-winx64 在D:\mysql-8.0.40-winx64目录下创建my.ini文件,并更新一下内容 [client] #客户端设置,即客户端默认的连接参数 # 设置mysql客户端连接服务…...
基于机器学习算法预测二手车市场数据清洗与分析平台(源码+定制+讲解) 基于Python的数据挖掘与可视化 二手车数据处理与分析系统开发 (机器学习算法预测)
博主介绍: ✌我是阿龙,一名专注于Java技术领域的程序员,全网拥有10W粉丝。作为CSDN特邀作者、博客专家、新星计划导师,我在计算机毕业设计开发方面积累了丰富的经验。同时,我也是掘金、华为云、阿里云、InfoQ等平台…...
【神经网络与深度学习】普通自编码器和变分自编码器的区别
引言 自编码器(Autoencoder,AE)和变分自编码器(Variational Autoencoder,VAE)是深度学习中广泛应用的两类神经网络结构,主要用于数据的压缩、重构和生成。然而,二者在模型设计、训练…...