集群开发学习(一)(安装GO和MySQL,K8S基础概念)
完成gin小任务
参考文档:
https://www.kancloud.cn/jiajunxi/ginweb100/1801414
https://github.com/hanjialeOK/going
最终代码地址:https://github.com/qinliangql/gin_mini_test.git
学习
1.安装go
wget https://dl.google.com/go/go1.20.2.linux-amd64.tar.gz
tar -C /usr/local -zxf go1.20.2.linux-amd64.tar.gz
export PATH=$PATH:/usr/local/go/bin
// All Tools installed by go are in $GOPATH.
export GOPATH=$PATH:/usr/local/go
export PATH=$PATH:$GOPATH/bin
// https://goproxy.cn is faster than aliyun.
export GOPROXY=https://goproxy.cn
验证安装是否成功
go version

hello world
mkdir hello && cd /hello
go mod init example/hello
创建一个hello.go
package mainimport "fmt"func main() {fmt.Println("Hello, World!")
}
在hello下运行
go run hello.go
做一个映射出来的
安装
go get github.com/gin-gonic/gin
我映射了端口8001
package mainimport ("github.com/gin-gonic/gin""net/http"
)func main() {router := gin.Default()router.GET("/", func(c *gin.Context) {c.String(http.StatusOK, "Hello World")})router.Run(":8001")
}
go run hello.go


2.安装MySQL
// For ubuntu 18.04
sudo apt install mysql-server
// start mysql
service mysql start
Change the password for mysql
// login
mysql -u root
// change the password for mysql
use mysql;
update user set authentication_string='' where user='root';
// newpassword: 123456
alter user 'root'@'localhost' identified with mysql_native_password by '123456';
// exit
quit
// restart mysql
service mysql restart
Create database and table.
mysql -u root -p
create database gobase;
use gobase;
CREATE TABLE `account` (`id` int(11) NOT NULL AUTO_INCREMENT,`name` varchar(20) NOT NULL,`email` varchar(50) NOT NULL,`password` varchar(30) NOT NULL,PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
查看数据库信息(先quit再重新打开mysql)
show databases;

查看table
use gobase;
\\ List Table info
show tables;
\\ Look structure of table
desc account;

Task
1.使用Gin创建一个API,允许用户通过提供姓名,电子邮件和密码来创建新账户。该API应验证所有字段是否存在以及电子邮件格式是否正确。
安装依赖
go get github.com/gin-gonic/gin
go get gorm.io/driver/mysql
go get gorm.io/gorm
代码:
package mainimport ("fmt""net/http""net/mail""github.com/gin-gonic/gin""gorm.io/driver/mysql""gorm.io/gorm"// "regexp"
)type UserInfo struct {ID int `form:"id"`Name string `form:"name" binding:"required"`Email string `form:"email" binding:"required,email"`Password string `form:"password" binding:"required,min=6"`
}func main() {// 创建一个默认的 Gin 路由器r := gin.Default()// 创建一个路由,允许用户提交新账户信息r.POST("/api/register", create)// 启动 Gin 服务器,默认监听在 8001 端口r.Run(":8001")
}// isValidEmail 检查电子邮件格式是否正确
func isValidEmail(email string) bool {_, err := mail.ParseAddress(email)// 如果解析正确,err会变为nilreturn err == nil
}func create(c *gin.Context) {// 绑定请求体到 UserInfo 结构体类型的form var form UserInfoif err := c.ShouldBindJSON(&form); err != nil {c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})return}// 检查电子邮件格式是否正确if !isValidEmail(form.Email) {c.JSON(http.StatusBadRequest, gin.H{"error": "Invalid email format"})return}// 打开数据库,3306是MySQL默认端口dsn := "root:123456@tcp(127.0.0.1:3306)/gobase"db, err := gorm.Open(mysql.Open(dsn), &gorm.Config{})if err != nil {c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})return}// check whether the name exists.var user UserInfodb.Table("account").Where("name = ?", form.Name).First(&user)if (user != UserInfo{}) {c.JSON(http.StatusBadRequest, gin.H{"error": "name exists!"})return}// check whether the email has been used.db.Table("account").Where("email = ?", form.Email).First(&user)if (user != UserInfo{}) {c.JSON(http.StatusBadRequest, gin.H{"error": fmt.Sprintf("email %s has been used!", form.Email)})return}// 保存用户到数据库(:= 对于没有声明的变量会自动声明)user = UserInfo{Name: form.Name, Email: form.Email, Password: form.Password}result := db.Table("account").Create(&user)if result.Error != nil {c.JSON(http.StatusBadRequest, gin.H{"error": result.Error})return}// 这里只是返回成功消息c.JSON(http.StatusOK, gin.H{"message": fmt.Sprintf("Account %s created successfully!",user.Name)})
}
测试代码:
-X 指定发送的请求类型为 POST 请求
-H 设置请求头,指定请求的内容类型为 JSON 格式
curl -X POST -H "Content-Type: application/json" -d '{"name":"QL","email":"qinl@example.com","password":"password"}' http://localhost:8001/api/register
查看数据库当前情况
service mysql start
mysql -u root -p
show databases;
use gobase;
show tables;
SELECT * FROM account;
quit

2.使用Gin实现一个API,允许用户通过提供电子邮件和密码来检索其帐户信息。该API应验证电子邮件和密码是否正确,然后返回用户信息。
新加代码:
// 新增路由,允许用户通过提供电子邮件和密码来检索其帐户信息,相当于登陆
r.POST("/api/login", login)/*
// 处理登录请求的函数 (这种必须要求输入完整的UserInfo类型信息才行,所以放弃)
func login(c *gin.Context) {// 绑定请求体到 UserInfo 结构体类型的 formvar form UserInfoif err := c.ShouldBindJSON(&form); err != nil {c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})return}// 打开数据库dsn := "root:123456@tcp(127.0.0.1:3306)/gobase"db, err := gorm.Open(mysql.Open(dsn), &gorm.Config{})if err != nil {c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})return}// 查询数据库中是否存在匹配的用户记录var user UserInforesult := db.Table("account").Where("email = ? AND password = ?", form.Email, form.Password).First(&user)if result.Error != nil {c.JSON(http.StatusBadRequest, gin.H{"error": "Invalid email or password"})return}// 返回匹配的用户信息c.JSON(http.StatusOK, gin.H{"message": fmt.Sprintf("Welcom user %s !", user.Name)})
}
*/func login(c *gin.Context) {// 绑定请求体到 UserInfo 结构体类型的 formemail := c.Query("email")password := c.Query("password")// 打开数据库dsn := "root:123456@tcp(127.0.0.1:3306)/gobase"db, err := gorm.Open(mysql.Open(dsn), &gorm.Config{})if err != nil {c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})return}// 查询数据库中是否存在匹配的用户记录var user UserInforesult := db.Table("account").Where("email = ? AND password = ?", email, password).First(&user)if result.Error != nil {c.JSON(http.StatusBadRequest, gin.H{"error": fmt.Sprintf("Invalid email:%s or password:%s",email,password)})return}// 返回匹配的用户信息c.JSON(http.StatusOK, gin.H{"message": fmt.Sprintf("Welcom user %s !", user.Name)})
}
测试代码:
# 正确案例
curl -X POST "http://localhost:8001/api/login?email=qinl@example.com&password=password"
# 错误案例
curl -X POST "http://localhost:8001/api/login?email=qinl@example.com&password=654321"
3.添加一个API,使用Gin允许用户更新其帐户信息。该API应验证用户是否已通过身份验证并且所有字段是否存在,然后将用户信息更新到数据库中。
安装依赖
go get github.com/golang-jwt/jwt/v5
更新的代码:
package mainimport ("fmt""net/http""net/mail""time""github.com/gin-gonic/gin""gorm.io/driver/mysql""gorm.io/gorm""github.com/golang-jwt/jwt/v5"
)// 创建一个 JWT(JSON Web Token)字符串。
// JWT 是一种用于在网络应用之间安全传递声明的开放标准。var jwtKey = []byte("my_secret_key") // 用于签名和验证 JWT 的密钥// input: email || output:string,error
func createToken(email string) (string, error) {token := jwt.NewWithClaims(jwt.SigningMethodHS256, jwt.MapClaims{"email": email,"exp": time.Now().Add(time.Minute * 10).Unix(), // 有效时长10分钟})return token.SignedString(jwtKey)
}func validateToken(tokenString string) (*jwt.Token, error) {token, err := jwt.Parse(tokenString, func(token *jwt.Token) (interface{}, error) {if _, ok := token.Method.(*jwt.SigningMethodHMAC); !ok {return nil, fmt.Errorf("Unexpected signing method: %v", token.Header["alg"])}return jwtKey, nil})if err != nil {return nil, err}if _, ok := token.Claims.(jwt.MapClaims); !ok || !token.Valid {return nil, fmt.Errorf("bad token.")}return token, nil
}func validateCookie(c *gin.Context) (*jwt.Token, error) {tokenString, err := c.Cookie("gin_cookie")if err != nil {return nil, err}token, err := validateToken(tokenString)if err != nil {return nil, err}return token, nil
}func main() {// 创建一个默认的 Gin 路由器r := gin.Default()// 创建一个路由,允许用户提交新账户信息r.POST("/api/register", create) // 新增路由,允许用户通过提供电子邮件和密码来检索其帐户信息,相当于登陆r.POST("/api/login", login)r.POST("/api/update", update) // 新增的路由,用于更新用户信息// 启动 Gin 服务器,默认监听在 8001 端口r.Run(":8001")
}func login(c *gin.Context) {// ...// Create the JWT string.token, err := createToken(user.Email)if err != nil {c.JSON(http.StatusInternalServerError, gin.H{"error": "Failed to create token"})return}// tell the user it's ok. 3600 是最大存活时间1hc.SetCookie("gin_cookie", token, 3600, "/", "", false, true)// 返回匹配的用户信息c.JSON(http.StatusOK, gin.H{"message": fmt.Sprintf("Welcom user %s !", user.Name)})
}func update(c *gin.Context) {token, err := validateCookie(c)if err != nil {c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})return}// get email from cookieemail := token.Claims.(jwt.MapClaims)["email"]// new passwordpassword := c.Query("password")name := c.Query("name")// updatedsn := "root:123456@tcp(127.0.0.1:3306)/gobase"db, err := gorm.Open(mysql.Open(dsn), &gorm.Config{})if err != nil {c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})return}// retrieve the user by email.var user UserInfodb.Table("account").Where("email = ?", email).First(&user)if (user == UserInfo{}) {c.JSON(http.StatusBadRequest, gin.H{"error": "this email has not been registered."})return}// 更新用户信息if name != "" {user.Name = name}if password != "" {user.Password = password}// 保存更新后的用户信息到数据库if err := db.Table("account").Save(&user).Error; err != nil {c.JSON(http.StatusInternalServerError, gin.H{"error": "Failed to update user"})return}// 返回更新成功的消息c.JSON(http.StatusOK, gin.H{"message": "User information updated successfully"})
}
测试代码,用 -i 可以更细致的看到信息,目前还是在curl里面传递cookie的
curl -i -X POST "http://localhost:8001/api/login?email=qinl@example.com&password=password"
curl -i -X POST "http://localhost:8001/api/update?password=newpassword" --cookie "gin_cookie=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJlbWFpbCI6InFpbmxAZXhhbXBsZS5jb20iLCJleHAiOjE3MTI4MDU0NTl9.VTLihEYTy-kWZjZhLrwpwIMuPgimpm-DVnYwvhoKnNs"
修改后的数据库

4. 使用Gin实现一个API,允许用户通过提供电子邮件和密码来删除其帐户。该API应验证电子邮件和密码是否正确,然后从数据库中删除用户帐户。
新加代码:
r.POST("/api/delete",delete) // 删除用户信息func delete(c *gin.Context) {email := c.Query("email")password := c.Query("password")// 打开数据库dsn := "root:123456@tcp(127.0.0.1:3306)/gobase"db, err := gorm.Open(mysql.Open(dsn), &gorm.Config{})if err != nil {c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})return}// 查询数据库中是否存在匹配的用户记录var user UserInforesult := db.Table("account").Where("email = ? AND password = ?", email, password).First(&user)if result.Error != nil {c.JSON(http.StatusBadRequest, gin.H{"error": "Invalid email or password"})return}// 删除用户账户if err := db.Table("account").Delete(&user).Error; err != nil {c.JSON(http.StatusInternalServerError, gin.H{"error": "Failed to delete account"})return}// 返回删除成功的消息c.JSON(http.StatusOK, gin.H{"message": fmt.Sprintf("Account %s deleted successfully",user.Name)})
}
测试代码:
curl -X POST "http://localhost:8001/api/delete?email=qinl@example.com&password=newpassword"

5. 添加一个API,使用Gin允许用户检索数据库中所有帐户的列表。
新加代码:
func show_all(c *gin.Context) {if _, err := validateCookie(c); err != nil {c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})return}// 打开数据库dsn := "root:123456@tcp(127.0.0.1:3306)/gobase"db, err := gorm.Open(mysql.Open(dsn), &gorm.Config{})if err != nil {c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})return}// 查询数据库,获取所有帐户列表var accountNames []stringif err := db.Table("account").Pluck("name", &accountNames).Error; err != nil {c.JSON(http.StatusInternalServerError, gin.H{"error": "Failed to retrieve accounts"})return}// 返回帐户列表给客户端c.JSON(http.StatusOK, accountNames)
}
测试代码:
# 先加两个用户
curl -X POST -H "Content-Type: application/json" -d '{"name":"QL","email":"qinl@example.com","password":"password"}' http://localhost:8001/api/register
curl -X POST -H "Content-Type: application/json" -d '{"name":"ZS","email":"zs@example.com","password":"password"}' http://localhost:8001/api/register
# 登录一个用户获取token
curl -i -X POST "http://localhost:8001/api/login?email=qinl@example.com&password=password"
# 用token,获取用户信息
curl -X POST "http://localhost:8001/api/show_all" --cookie "gin_cookie=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJlbWFpbCI6InFpbmxAZXhhbXBsZS5jb20iLCJleHAiOjE3MTI4MDc0OTB9.hoB7TY0TorAlmdtm-jyqb8U5nSAehmP7d2n5EjSE1r8"
[“QL”,“ZS”]
6. 调研了解目前主流的登录鉴权方式,选择一个在你的项目中进行实现。
主流鉴权方式:
-
基于Token的认证(Token-based Authentication):用户在登录成功后会收到一个令牌(Token),之后每次请求都需要在请求头中携带这个令牌进行验证。常见的Token包括JWT(JSON Web Token)和OAuth2 Token。
-
OAuth2认证(OAuth2 Authentication):OAuth2是一种开放标准,允许用户授权第三方应用访问其资源。用户可以通过第三方认证提供者(如Google、Facebook等)进行登录,然后授权给应用访问其资源的权限。
-
基于Session的认证(Session-based Authentication):用户在登录成功后,服务器会为其创建一个会话(Session),并将会话ID存储在Cookie中,用户在后续的请求中都会携带这个会话ID。服务器通过会话ID来验证用户的身份和权限。
原本的是基于token做的,这里改为基于session做
安装依赖:
go get github.com/gorilla/sessions
新代码:
// 定义一个全局的会话存储对象
var store = sessions.NewCookieStore([]byte("my-secret"))// 创建会话并将用户ID存储在会话中
session, _ := store.Get(c.Request, "session-name")
session.Values["userID"] = user.ID
session.Save(c.Request, c.Writer)// 获取会话中的用户IDsession, _ := store.Get(c.Request, "session-name")_, ok := session.Values["userID"].(int)if !ok {c.JSON(http.StatusBadRequest, gin.H{"error": "User not authenticated"})return}
测试代码:
# 登录一个用户
curl -i -X POST "http://localhost:8001/api/login?email=qinl@example.com&password=password"
# 用token,获取用户信息
curl -X POST "http://localhost:8001/api/show_all" --cookie "session-name=MTcxMjgyNjI1NHxEdi1CQkFFQ180SUFBUkFCRUFBQUhmLUNBQUVHYzNSeWFXNW5EQWdBQm5WelpYSkpSQU5wYm5RRUFnQUV8hXB2Vl_OaBCvi71u6KLgrh96uhu-Irt-CAzSbxFBMeY="
K8S 概念理解
核心
-
Namespace(命名空间):
- Namespace是Kubernetes中用于将集群中的资源划分为不同逻辑组的一种机制。
- 它允许用户在同一集群中创建多个虚拟集群。
- 命名空间提供了一种在不同组织或项目之间隔离资源的方法,以及控制资源访问和使用的方法。
- 默认情况下,Kubernetes提供了一些预定义的命名空间,如"default"用于用户创建的资源,以及"kube-system"用于Kubernetes系统组件。
-
Pod(Pod):
- Pod是Kubernetes中最小的部署和管理单位。
- 它是一个或多个相关容器的组合,共享网络和存储资源,并在同一宿主机上运行。
- Pod可以包含单个容器(单容器Pod)或多个容器(多容器Pod),这些容器可以共享网络命名空间和存储卷。
- Pod可以用来运行应用程序、批处理作业或其他需要共享资源的任务。
-
Deployment(部署):
- Deployment是Kubernetes中用于管理Pod副本的控制器。
- 它定义了应用程序或服务的期望状态,并确保集群中运行的Pod数量符合该状态。
- Deployment允许用户轻松地创建、更新和扩展Pod副本,以及执行滚动升级和回滚操作。
- 通过Deployment,用户可以指定应用程序的副本数量、容器镜像和更新策略等参数。
-
Service(服务):
- Service是Kubernetes中用于将Pod公开为网络服务的抽象。
- 它为Pod提供了一个稳定的网络端点,允许其他应用程序或服务通过网络访问它们。
- Service可以通过标签选择器将一组Pod组合成一个逻辑集,并将流量负载均衡到这些Pod之间。
- Kubernetes支持多种类型的Service,包括ClusterIP、NodePort、LoadBalancer和ExternalName等。
综上所述,Namespace用于组织和隔离资源,Pod是最小的部署单元,Deployment用于管理Pod副本,Service提供网络访问入口,使应用程序或服务可以在集群内部或外部可达。这些概念共同构成了Kubernetes的核心功能,为容器化应用程序的部署、管理和扩展提供了强大的支持。
了解
-
Node(节点):
- Node是Kubernetes集群中的工作节点,用于运行应用程序和服务的实际工作负载。
- 每个Node都是一个单独的物理机器或虚拟机,它们一起组成了Kubernetes集群。
- Node由Kubernetes Master进行管理和监控,并承载了容器运行时引擎(如Docker或containerd)来运行Pod。
-
Cluster(集群):
- Cluster是由一组Node组成的Kubernetes环境,用于运行和管理容器化应用程序和服务。
- 它包括一个Master节点和一组工作节点,所有这些节点共同协作以提供高可用性、自动扩展和自我修复的特性。
-
Resource Quota(资源配额):
- Resource Quota是Kubernetes中的一种资源管理机制,用于限制Namespace中资源的使用量。
- 它允许集群管理员为每个Namespace设置配额,以控制Pod、CPU、内存、存储等资源的使用量,防止资源耗尽和过度使用。
-
ConfigMap(配置映射):
- ConfigMap是Kubernetes中用于存储配置数据的API对象。
- 它允许将配置数据(如环境变量、配置文件等)从应用程序中解耦,并将其存储在集群中的ConfigMap对象中。
- ConfigMap可以在Pod中作为卷或环境变量挂载,使应用程序可以动态地读取配置数据。
-
Role(角色)和RoleBinding(角色绑定):
- Role和RoleBinding是Kubernetes中用于授权和访问控制的两个重要对象。
- Role定义了一组权限规则,允许用户或服务账户对指定的资源执行特定的操作。
- RoleBinding将Role绑定到用户、组或ServiceAccount,并为其分配相应的权限,以控制对资源的访问。
-
Service Account(服务账户):
- Service Account是Kubernetes中用于身份验证和授权的一种机制。
- 它为Pod中运行的应用程序提供了一个身份标识,并允许它们与Kubernetes API进行交互。
- 每个Namespace都有一个默认的Service Account,可以为Pod分配具有不同权限的Service Account。
-
PersistentVolume(持久化卷)和PersistentVolumeClaim(持久化卷声明):
- PersistentVolume(PV)是Kubernetes中用于存储数据的持久化存储资源。
- PersistentVolumeClaim(PVC)是用户向Kubernetes请求PV的一种机制,它定义了用户对存储资源的需求和要求。
- PVC允许用户独立于底层存储实现和配置,并根据需要动态地请求和释放PV。
配置.kube文件
mkdir ~/.kube
# 需要管理员权限才能复制配置文件
sudo cp /etc/kubernetes/admin.conf ~/.kube/config
# 把文件权限改为自己,xxx就是自己的用户名
sudo chown -R qinl:qinl ~/.kube/
# 修改为自己的命名空间,vim编辑~/.kube/config文件,在context一栏加上一行,然后保存并退出即可:
nano ~/.kube/config
- context:cluster: kubernetesuser: kubernetes-adminnamespace: xxx # 这里加上自己的命名空间xxx,一般用自己的用户名name: kubernetes-admin@kubernetes
# 创建自己的命名空间,和上面的xxx对应
kubectl create ns qinl
测试
kubectl get po

相关文章:
集群开发学习(一)(安装GO和MySQL,K8S基础概念)
完成gin小任务 参考文档: https://www.kancloud.cn/jiajunxi/ginweb100/1801414 https://github.com/hanjialeOK/going 最终代码地址:https://github.com/qinliangql/gin_mini_test.git 学习 1.安装go wget https://dl.google.com/go/go1.20.2.linu…...
[Kubernetes[K8S]集群:Slaver从节点初始化和Join]:添加到主节点集群内
文章目录 操作流程:上篇主节初始化地址:前置:Docker和K8S安装版本匹配查看0.1:安装指定docker版本 **[1 — 8] ** [ 这些步骤主从节点前置操作一样的 ]一:主节点操作 查看主机域名->编辑域名->域名配置二&#x…...
redis复习笔记08(小滴课堂)
案例实战需求之大数据下的用户画像标签去重 我们就简单的做到了去重了。 案例实战社交应用里面之关注、粉丝、共同好友案例 这就是我们set的一个应用。 案例实战之SortedSet用户积分实时榜单最佳实践 准备积分类对象: 我们加上构造方法和判断相等的equals和hascod…...
在线课程平台LearnDash评测 – 最佳 WordPress LMS插件
在我的LearnDash评测中,我探索了流行的 WordPress LMS 插件,该插件以其用户友好的拖放课程构建器而闻名。我深入研究了各种功能,包括课程创建、测验、作业、滴灌内容、焦点模式、报告、分析和管理工具。 我的评测还讨论了套餐和定价选项&…...
OpenDDS-3.27构建与用法
一、OpenDDS-3.27构建 ./configure To enable Java bindings, use ./configure --java make 二、运行Messenger Example: source setenv.sh For the C example:cd DevGuideExamples/DCPS/Messenger For the Java example:cd java/tests/mes…...
计算机网络——MAC地址和IP地址
目录 前言 引入 MAC地址与IP地址 IP地址和MAC地址是什么?如何起作用的? MAC地址如何表示与确定网卡在网络中的确定位置? DHCP协议自动帮我们配置 操作系统是如何知道对方的MAC地址的? 前言 本博客是博主用于复习计算机网络…...
Unity构建详解(7)——AssetBundle格式解析
【文件格式】 文件可以分为文本文件、图片文件、音频文件、视频文件等等,我们常见的这些文件都有行业内的标准格式,其意味着按照一定的规则和规范去保存读取文件,可以获取我们想要的数据。 有些软件会有自己的文件格式,会按照其…...
前端对接fastGPT流式数据+打字机效果
首先在对接api时 参数要设置stream: true, const data {chatId: abc,stream: true,//这里true返回流式数据detail: false,variables: {uid: sfdsdf,name: zhaoyunyao,},messages: [{ content: text, role: user }]}; 不要用axios发请求 不然处理不了流式数据 我这里使用fetch …...
避免使用第三方工具完成电脑环境检测
0. 简介 在之前配置各种深度学习环境的时候经常需要先检测一下电脑的软硬件环境,其实整个过程比较重复和固定,所以我们是否有可能一键检测Python版本、PIP版本、Conda版本、CUDA版本、电脑系统、CPU核数、CPU频率、内存、硬盘等内容这是很多Deepper苦恼…...
vue 中 mixin 的应用场景,原理和合并规则
应用场景 多个组件的相同逻辑可以提出去来一个公共的 mixin 原理 Mixin 的工作原理是将 Mixin 中的选项合并到组件的选项中 合并规则 优先处理 mixinsprops 、method、inject、computed 同名的使用组件内的,不使用mixin 的data 进行合并生命周期和watch 先执行…...
点击按钮(文字)调起elementUI大图预览
时隔一年,我又回来了 ~ 最近在做后台,遇到一个需求,就是点击“查看详情”按钮,调起elementUI的大图预览功能,预览多张图片,如下图: 首先想到的是使用element-ui的el-image组件,但它是…...
全面学习SpringCloud框架指南
要深入学习Spring Cloud框架,你需要系统地掌握其核心组件和概念,并了解如何在实际项目中应用这些知识。以下是一些关键的学习点和相应的学习内容: 一共分为10个模块包括: 1、微服务架构基础: 理解微服务架构的概念和优势。 学习单体架构向微服务架构演进的过程。 掌握…...
5G智慧水利数字孪生可视化平台,推进水利行业数字化转型
5G智慧水利数字孪生可视化平台,推进水利行业数字化转型。随着5G技术的快速发展,越来越多的行业开始探索数字化转型的道路。水利行业作为国民经济的重要支柱,也面临着数字化转型的迫切需求。5G智慧水利数字孪生可视化平台作为水利行业数字化转…...
新手入门:大语言模型训练指南
在这个信息爆炸的时代,人工智能技术正以前所未有的速度渗透到我们生活的方方面面。从智能手机上的语音助手到自动驾驶汽车,AI的应用无处不在。而在这些令人惊叹的技术背后,大语言模型(LLM)扮演着至关重要的角色。它们不…...
Win11 WSL2 install Ubuntu20.04 and Seismic Unix
Win11系统,先启用或关闭Windows功能,勾选“适用于Linux的Windows子系统”和“虚拟机平台”两项 设置wsl默认版本为wsl2,并更新 wsl --list --verbose # 查看安装版本及内容 wsl --set-default-version 2 # 设置wsl默认版本为wsl2 # 已安装…...
rust使用print控制台打印输出五颜六色的彩色红色字体
想要在控制台打印输出彩色的字体,可以使用一些已经封装好的依赖库,比如ansi_term这个依赖库,官方依赖库地址:https://crates.io/crates/ansi_term 安装依赖: cargo add ansi_term 或者在Cargo.toml文件中加入&#…...
贪心算法|435.无重叠区间
力扣题目链接 class Solution { public:// 按照区间右边界排序static bool cmp (const vector<int>& a, const vector<int>& b) {return a[1] < b[1];}int eraseOverlapIntervals(vector<vector<int>>& intervals) {if (intervals.siz…...
C++的并发世界(七)——互斥锁
0.死锁的由来 假设有两个线程T1和T2,它们需要对两个互斥量mtx1和mtx2进行访问。而且需要按照以下顺序获取互斥量的所有权: -T1先获取mte1的所有权,再获取mt2的所有权。 -T2先获取 mtx2的所有权。再铁取 mtx1的所有权。 如果两个线程同时执行,…...
NI-LabView的DAQ缺少或丢失的解决办法(亲测有效)
DAQmx在Labview中不显示或缺失 问题:在NI Packasge Manager安装完DAQ后在labview中不显示控件解决办法 问题:在NI Packasge Manager安装完DAQ后在labview中不显示控件 在打开测量I/O时,见不到 DAQmx,或者在Express中见不到DAQ助手…...
cesium 调整3dtiles的位置 世界坐标下 相对坐标下 平移矩阵
cesium调整3dtiles的位置用到的是平移矩阵,原理是在世界坐标系中用偏移点减去原始点得到一个平移向量,再根据这个向量得到平移矩阵。 原始点:一般是模型的中心点位置,可通过模型的包围盒得到偏移点:可分为两种情况&…...
MySQL 隔离级别:脏读、幻读及不可重复读的原理与示例
一、MySQL 隔离级别 MySQL 提供了四种隔离级别,用于控制事务之间的并发访问以及数据的可见性,不同隔离级别对脏读、幻读、不可重复读这几种并发数据问题有着不同的处理方式,具体如下: 隔离级别脏读不可重复读幻读性能特点及锁机制读未提交(READ UNCOMMITTED)允许出现允许…...
UDP(Echoserver)
网络命令 Ping 命令 检测网络是否连通 使用方法: ping -c 次数 网址ping -c 3 www.baidu.comnetstat 命令 netstat 是一个用来查看网络状态的重要工具. 语法:netstat [选项] 功能:查看网络状态 常用选项: n 拒绝显示别名&#…...
HTML 列表、表格、表单
1 列表标签 作用:布局内容排列整齐的区域 列表分类:无序列表、有序列表、定义列表。 例如: 1.1 无序列表 标签:ul 嵌套 li,ul是无序列表,li是列表条目。 注意事项: ul 标签里面只能包裹 li…...
【项目实战】通过多模态+LangGraph实现PPT生成助手
PPT自动生成系统 基于LangGraph的PPT自动生成系统,可以将Markdown文档自动转换为PPT演示文稿。 功能特点 Markdown解析:自动解析Markdown文档结构PPT模板分析:分析PPT模板的布局和风格智能布局决策:匹配内容与合适的PPT布局自动…...
生成 Git SSH 证书
🔑 1. 生成 SSH 密钥对 在终端(Windows 使用 Git Bash,Mac/Linux 使用 Terminal)执行命令: ssh-keygen -t rsa -b 4096 -C "your_emailexample.com" 参数说明: -t rsa&#x…...
vue3+vite项目中使用.env文件环境变量方法
vue3vite项目中使用.env文件环境变量方法 .env文件作用命名规则常用的配置项示例使用方法注意事项在vite.config.js文件中读取环境变量方法 .env文件作用 .env 文件用于定义环境变量,这些变量可以在项目中通过 import.meta.env 进行访问。Vite 会自动加载这些环境变…...
Web 架构之 CDN 加速原理与落地实践
文章目录 一、思维导图二、正文内容(一)CDN 基础概念1. 定义2. 组成部分 (二)CDN 加速原理1. 请求路由2. 内容缓存3. 内容更新 (三)CDN 落地实践1. 选择 CDN 服务商2. 配置 CDN3. 集成到 Web 架构 …...
2025季度云服务器排行榜
在全球云服务器市场,各厂商的排名和地位并非一成不变,而是由其独特的优势、战略布局和市场适应性共同决定的。以下是根据2025年市场趋势,对主要云服务器厂商在排行榜中占据重要位置的原因和优势进行深度分析: 一、全球“三巨头”…...
#Uniapp篇:chrome调试unapp适配
chrome调试设备----使用Android模拟机开发调试移动端页面 Chrome://inspect/#devices MuMu模拟器Edge浏览器:Android原生APP嵌入的H5页面元素定位 chrome://inspect/#devices uniapp单位适配 根路径下 postcss.config.js 需要装这些插件 “postcss”: “^8.5.…...
论文笔记——相干体技术在裂缝预测中的应用研究
目录 相关地震知识补充地震数据的认识地震几何属性 相干体算法定义基本原理第一代相干体技术:基于互相关的相干体技术(Correlation)第二代相干体技术:基于相似的相干体技术(Semblance)基于多道相似的相干体…...
