当前位置: 首页 > news >正文

Golang教程六(单元测试,反射,网络编程,部署)

目录

一、单元测试

单元测试 

 子测试

 TestMain

二、反射

类型判断

通过反射获取值

通过反射修改值

结构体反射

利用tag修改结构体的某些值

调用结构体方法

orm的一个小案例

对反射的一些建议

三、网络编程

socket编程

websocket编程

四、部署

打包命令

交叉编译


一、单元测试

Go语言中自带有一个轻量级的测试框架testing和自带的go test命令来实现单元测试和性能测试,testing框架和其他语言的测试框架相似,可以基于这个框架写针对相应函数的测试用例,也可以基于该框架写相应的压力测试用例。通过单元测试,可以解决:

  1. 确保每个函数是可运行,并且运行结果是正确的
  2. 确保写出来的代码性能是好的
  3. 单元测试能及时的发现程序设计或实现的逻辑错误,使问题暴露,便于问题的定位解决,而性能测试的重点在于发现程序设计上的一些问题,让程序能够在高并发的情况下还能保持稳定

Go 语言推荐测试文件和源代码文件放在一块,测试文件以 _test.go 结尾

注意点:

  1. 测试用例文件名必须以_test.go结尾
  2. 测试用例函数必须以Test开头,一般来说就是Test+被测试的函数名 

单元测试 

例如我现在有两个用于计算的文件,叫calc.go

package mainfunc Add(a int, b int) int {return a + b
}func Mul(a int, b int) int {return a * b
}

那么我的测试文件就是calc_test.go

package mainimport "testing"func TestAdd(t *testing.T) {if ans := Add(1, 2); ans != 3 {// 如果不符合预期,那就是测试不通过t.Errorf("1 + 2 expected be 3, but %d got", ans)}if ans := Add(-10, -20); ans != -30 {t.Errorf("-10 + -20 expected be -30, but %d got", ans)}
}

go test // 可以运行某个包下的所有测试用例

-v 参数会显示每个用例的测试结果

-run参数可以指定测试某个函数

单元测试框架提供的日志方法

方 法备 注测试结果
Log打印日志,同时结束测试PASS
Logf格式化打印日志,同时结束测试PASS
Error打印错误日志,同时结束测试FAIL
Errorf格式化打印错误日志,同时结束测试FAIL
Fatal打印致命日志,同时结束测试FAIL
Fatalf格式化打印致命日志,同时结束测试FAIL

 子测试

如果需要给一个函数,调用不同的测试用例,可以使用子测试

子测试里面的Fatal,是不会终止程序的

package mainimport "testing"func TestAdd(t1 *testing.T) {t1.Run("add1", func(t *testing.T) {if ans := Add(1, 2); ans != 3 {// 如果不符合预期,那就是测试不通过t.Fatalf("1 + 2 expected be 3, but %d got", ans)}})t1.Run("add2", func(t *testing.T) {if ans := Add(-10, -20); ans != -30 {t.Fatalf("-10 + -20 expected be -30, but %d got", ans)}})}

如果测试用例很多,还可以用一个类似表格去表示

package mainimport ("testing"
)func TestAdd(t *testing.T) {cases := []struct {Name           stringA, B, Expected int}{{"a1", 2, 3, 5},{"a2", 2, -3, -1},{"a3", 2, 0, 2},}for _, c := range cases {t.Run(c.Name, func(t *testing.T) {if ans := Add(c.A, c.B); ans != c.Expected {t.Fatalf("%d * %d expected %d, but %d got",c.A, c.B, c.Expected, ans)}})}
}

 TestMain

它是测试的入口

我们可以在TestMain里面实现测试流程的生命周期

package mainimport ("fmt""os""testing"
)// 测试前执行
func setup() {fmt.Println("Before all tests")
}// 测试后执行
func teardown() {fmt.Println("After all tests")
}func Test1(t *testing.T) {fmt.Println("I'm test1")
}func Test2(t *testing.T) {fmt.Println("I'm test2")
}// 必须叫这个名字  测试主入口
func TestMain(m *testing.M) {// 测试前执行setup()code := m.Run()// 测试后执行teardown()os.Exit(code)
}

二、反射

类型判断

判断一个变量是否是结构体,切片,map

package mainimport ("fmt""reflect"
)func refType(obj any) {typeObj := reflect.TypeOf(obj)fmt.Println(typeObj, "+", typeObj.Kind())// 去判断具体的类型switch typeObj.Kind() {case reflect.Slice:fmt.Println("切片")case reflect.Map:fmt.Println("map")case reflect.Struct:fmt.Println("结构体")case reflect.String:fmt.Println("字符串")}
}func main() {refType(struct{ Name string }{Name: "os_lee"})name := "os_lee"refType(name)refType([]string{"os_lee"})
}

通过反射获取值

package mainimport ("fmt""reflect"
)func refValue(obj any) {value := reflect.ValueOf(obj)fmt.Println(value, "+", value.Type())switch value.Kind() {case reflect.Int:fmt.Println("Int=", value.Int())case reflect.Struct:fmt.Println("Interface=", value.Interface())case reflect.String:fmt.Println("String=", value.String())}
}func main() {refValue(struct{ Name string }{Name: "os_lee"})name := "os_lee"refValue(name)refValue([]string{"os_lee"})
}

通过反射修改值

注意,如果需要通过反射修改值,必须要传指针,在反射中使用Elem取指针对应的值

结构体反射

读取json标签对应的值,如果没有就用属性的名称

这个示例很简单,没有处理-和omitempty的情况

package mainimport ("fmt""reflect"
)type Student struct {Name stringAge  int `json:"age"`
}func main() {s := Student{Name: "os_lee",Age:  24,}t := reflect.TypeOf(s)v := reflect.ValueOf(s)for i := 0; i < t.NumField(); i++ {field := t.Field(i)jsonField := field.Tag.Get("json")if jsonField == "" {// 说明json的tag是空的jsonField = field.Name}fmt.Printf("Name: %s, type: %s, json: %s, value: %v\n", field.Name, field.Type, jsonField, v.Field(i))}
}

利用tag修改结构体的某些值

例如,结构体tag中有big的标签,就将值大写

package mainimport ("fmt""reflect""strings"
)type Student struct {Name string `big:"name"`Addr string
}func main() {s := Student{Name: "os",Addr: "bj",}t := reflect.TypeOf(s)v := reflect.ValueOf(&s).Elem()for i := 0; i < t.NumField(); i++ {field := t.Field(i)bigField := field.Tag.Get("big")// 判断类型是不是字符串if field.Type.Kind() != reflect.String {continue}if bigField == "" {continue}// 修改值valueFiled := v.Field(i)valueFiled.SetString(strings.ToTitle(valueFiled.String()))}fmt.Println(s)
}

调用结构体方法

如果结构体有call这个名字的方法,就执行它

package mainimport ("fmt""reflect"
)type Student struct {Name stringAge  int
}func (Student) Look(name string) {fmt.Println("look name:", name)
}func (Student) See(name string) {fmt.Println("see name:", name)
}func main() {s := Student{Name: "os",Age:  21,}t := reflect.TypeOf(s)v := reflect.ValueOf(s)for i := 0; i < t.NumMethod(); i++ {methodType := t.Method(i)fmt.Println(methodType.Name, methodType.Type)if methodType.Name != "See" {continue}methodValue := v.Method(i)methodValue.Call([]reflect.Value{reflect.ValueOf("lee"), // 注意这里的类型})}
}

orm的一个小案例

package mainimport ("errors""fmt""reflect""strings"
)type Student struct {Name string `oslee-orm:"name"`Age  int    `oslee-orm:"age"`
}type UserInfo struct {Id   int    `oslee-orm:"id"`Name string `oslee-orm:"name"`Age  int    `oslee-orm:"age"`
}// sql, err := Find(Student{}, "name = ? and age = ?", "os_lee", 18)
func Find(obj any, query ...any) (sql string, err error) {// Find(Student, "name = ?", "os")// 希望能够生成 select name, age from  where  name = 'os't := reflect.TypeOf(obj)//v := reflect.ValueOf(obj)// 首先得是结构体对吧if t.Kind() != reflect.Struct {err = errors.New("非结构体")return}// 拿全部字段// 拼接条件// 第二个参数,中的问号,就决定后面还能接多少参数var where stringif len(query) > 0 {// 有第二个参数,校验第二个参数中的?个数,是不是和后面的个数一样q := query[0] // 理论上还要校验第二个参数的类型if strings.Count(q.(string), "?")+1 != len(query) {err = errors.New("参数个数不对")return}// 拼接where语句// 将?号带入后面的参数for _, a := range query[1:] {// 替换q// 这里要判断a的类型at := reflect.TypeOf(a)switch at.Kind() {case reflect.Int:q = strings.Replace(q.(string), "?", fmt.Sprintf("%d", a.(int)), 1)case reflect.String:q = strings.Replace(q.(string), "?", fmt.Sprintf("'%s'", a.(string)), 1)}}where += "where " + q.(string)}// 如果没有第二个参数,就是查全部// 拼接select// 拿所有字段,取oslee-orm对应的值var columns []stringfor i := 0; i < t.NumField(); i++ {field := t.Field(i)f := field.Tag.Get("oslee-orm")// 不考虑是空的情况columns = append(columns, f)}// 结构体的小写名字+s做表名name := strings.ToLower(t.Name()) + "s"// 拼接最后的sqlsql = fmt.Sprintf("select %s from %s %s", strings.Join(columns, ","), name, where)return
}func main() {sql, err := Find(Student{}, "name = ? and age = ?", "os_lee", 18)fmt.Println(sql, err) // select name,age from students where name = 'os_lee' and age = 18sql, err = Find(UserInfo{}, "id = ?", 1)fmt.Println(sql, err) // select id,name,age from userinfos where id = 1
}

对反射的一些建议

如果是写一下框架,偏底层工具类的操作

不用反射确实不太好写,但是如果是在业务上,大量使用反射就不太合适了

因为反射的性能没有正常代码高,会慢个一到两个数量级

使用反射可读性也不太好,并且也不能在编译期间发生错误

三、网络编程

socket编程

参考:5.网络编程-socker(golang版)-CSDN博客

websocket编程

参考:4.网络编程-websocket(golang)-CSDN博客

四、部署

go项目的部署特别简单,编写完成之后,只需要执行go build即可打包为可执行文件
注意,这个操作是不同平台不一样的
windows下打包就是exe文件,linux下打包就是二进制文件

打包命令

go build

打当前目录下的main包,注意,只能有一个main函数的包

go build xxx.go

打当前目录下,xxx.go的包,这个包必须得是一个main包,不然没有效果

go build -o main.exe xxx.go

强制对输出的文件进行重命名

-o参数必须得在文件的前面

交叉编译

什么是交叉编译呢,就是在windows上,我开发的go程序,我也能打包为linux上的可执行程序

例如在windows平台,打linux的包

注意,执行set这个命令,一定得要是在cmd的命令行下,powershell是无效的 

set CGO_ENABLED=0  
set GOOS=linux  
set GOARCH=amd64  
go build -o main main.go

 CGO_ENABLED : CGO 表示 golang 中的工具,CGO_ENABLED=0 表示 CGO 禁用,交叉编译中不能使用 CGO GOOS : 环境变量用于指定目标操作系统,mac 对应 darwin,linux 对应 linux,windows 对应 windows ,还有其它的 freebsd、android 等

GOARCH:环境变量用于指定处理器的类型,386 也称 x86 对应 32位操作系统、amd64 也称 x64 对应 64 位操作系统,arm 这种架构一般用于嵌入式开发。比如 Android , iOS , Win mobile 等

为了方便呢,可以在项目的根目录下写一个bat文件

这样就能快速构建了

然后放到linux服务器下,设置文件权限就可以直接运行了

chmod +x main
./main

再次注意啊,以后打包web项目的时候,配置文件和静态文件等这些非go程序,是要一起复制到目标服务器里面的

参考:Go 学习笔记(37)— 标准命令行工具(go build 跨平台编译、交叉编译、go clean、go run、go fmt、go install、go get、go vet)-CSDN博客

相关文章:

Golang教程六(单元测试,反射,网络编程,部署)

目录 一、单元测试 单元测试 子测试 TestMain 二、反射 类型判断 通过反射获取值 通过反射修改值 结构体反射 利用tag修改结构体的某些值 调用结构体方法 orm的一个小案例 对反射的一些建议 三、网络编程 socket编程 websocket编程 四、部署 打包命令 交叉编译…...

mybatis进阶篇-执行CRUD操作-typeAliases别名-接口绑定

目录结构 1.创建数据表&#xff08;book&#xff09; # 创建book表 create table book(id int auto_increment primary key,name varchar(255) ,price double ,num int );2.mybatis.xml配置文件 <?xml version"1.0" encoding"UTF-8" ?> <!DOC…...

C#面:泛型的主要约束和次要约束是什么

在 C# 中&#xff0c;泛型的约束是用来限制泛型类型参数的行为和能力的。 主要约束和次要约束是两种不同的约束方式。 主要约束&#xff08;Primary Constraint&#xff09;&#xff1a; 主要约束指定了泛型类型参数必须满足的最基本的条件&#xff0c;它可以是一个类、一个接…...

Java使用documents4j将word和excel转pdf

pom.xml添加documents4j依赖 <!-- documents4j --> <dependency><groupId>com.documents4j</groupId><artifactId>documents4j-local</artifactId><version>1.0.3</version> </dependency> <!-- documents4j 转 wor…...

使用策略模式实现 Spring 分布式和单机限流

我们可以使用策略模式来统一单机限流和分布式限流的实现,提高代码的可扩展性和可维护性。 思路是定义一个 RateLimitStrategy 接口,并分别实现单机限流策略 LocalRateLimitStrategy 和分布式限流策略 DistributedRateLimitStrategy。在 AOP 切面中,根据配置决定使用哪种限流策…...

@CrossOrigin注解解决跨域问题

文章目录 一、什么是跨域二、CrossOrigin注解是干什么用的三、用法 一、什么是跨域 跨域&#xff0c;指的是浏览器不能执行其他网站的脚本。它是由浏览器的同源策略造成的&#xff0c;是浏览器对JavaScript施加的安全限制。 所谓同源是指&#xff0c;域名&#xff0c;协议&…...

【力扣】45. 跳跃游戏 II

Problem: 45. 跳跃游戏 II 文章目录 问题思路复杂度Code 问题 思路 核心思路&#xff0c;例如nums[i]5&#xff0c;那么最远能跳五步&#xff1b; //那么在这接下来1-5范围内&#xff0c;哪个能让我跳的最远&#xff0c;这个最远指的是 -------------------------------------…...

【Python基础】19.eval函数的使用

eval函数 eval()将字符串转变为有效的表达式来求值并返回对应的结果 基础数据计算 In [1]: eval("1 1") Out[1]: 2字符串重复 In [2]: eval (" * * 10") Out[2]: **********字符串转为列表 In [3]: type(eval("[1,2,3,4,5]")) Out[3]: lis…...

对装饰器模式的理解

目录 一、场景二、面对场景中的新需求&#xff0c;我们怎么办&#xff1f;1、暴力法&#xff1a;直接修改原有的代码。2、子类继承法&#xff1a;既然要增强行为&#xff0c;那我搞一个子类&#xff0c;覆写不就完事了&#xff1f;3、装饰器模式 三、对装饰器模式的思考1、从代…...

在替换微软AD的CA证书服务AD CS前,要先做哪些准备工作?

AD CS是什么 关于这个问题&#xff0c;有几个概念需要先弄明白&#xff1a;PKI、CA、数字证书。 PKI&#xff08;Public Key Infrastructure&#xff0c;公钥基础设施&#xff09;是提供公钥加密和数字签名服务的系统或平台&#xff0c;实现基于公钥密码体制的密钥和证书的产生…...

Java中的System

文章目录 概要小结 概要 在Java中&#xff0c;System类提供了一些静态方法来实现与系统相关的操作。以下是System类中常用的方法及其含义&#xff1a; System.currentTimeMillis()&#xff1a;返回当前时间&#xff08;以毫秒为单位&#xff09;自1970年1月1日00:00:00 GMT以来…...

Mybites一对多collection

Goods实体属性&#xff1a; private List<GoodsImg> goodsImgList; private String id; private String name; GoodsImg实体属性&#xff1a; private String id; private String fid; private String imgpath; …...

基于springboot实现图书进销存管理系统项目【项目源码+论文说明】计算机毕业设计

基于springboot实现图书进销存管理系统演示 摘要 随着信息技术在管理上越来越深入而广泛的应用&#xff0c;管理信息系统的实施在技术上已逐步成熟。本文介绍了图书进销存管理系统的开发全过程。通过分析图书进销存管理系统管理的不足&#xff0c;创建了一个计算机管理图书进销…...

敏捷开发:想要快速交付就必须舍弃产品质量?

随着敏捷的推广与应用&#xff0c;如今已经成为了最有效的团队级别的方法论&#xff0c;越来越多的软件和 IT 团队正在采用敏捷&#xff0c;但是你在敏捷吗&#xff1f; 自从那一群充满影响力的软件从业者聚集在一起并发布了《敏捷宣言》以来&#xff0c;已经过去了 23 年。敏…...

SNMP-详解指南

目录 SNMP介绍 SNMP的工作机制轮询 SNMP的MIB&#xff08;管理信息库&#xff09; SNMP是基于UDP协议 SNMP介绍 SNMP&#xff08;Simple Network Management Protocol&#xff0c;简单网络管理协议&#xff09;是一种广泛应用于互联网上的网络管理协议。它提供了一种标准化…...

vue-router 原理【详解】hash模式 vs H5 history 模式

hash 模式 【推荐】 路由效果 在不刷新页面的前提下&#xff0c;根据 URL 中的 hash 值&#xff0c;渲染对应的页面 http://test.com/#/login 登录页http://test.com/#/index 首页 核心API – window.onhashchange 监听 hash 的变化&#xff0c;触发视图更新 window.onhas…...

WebGl/Three 粒子系统 人物破碎及还原运动

粒子 首先&#xff0c;加载模型&#xff0c;这是万千粒子的前身&#xff0c;模型对象由很多面构成&#xff0c;这些面又是由各个点构成的&#xff0c;所以可以将模型的几何体对象geometry赋给粒子对象&#xff0c;粒子物体用Points方式渲染 bloader.load("obj/female02/Fe…...

华为OD-C卷-分披萨[100分]

题目描述 "吃货"和"馋嘴"两人到披萨店点了一份铁盘(圆形)披萨,并嘱咐店员将披萨按放射状切成大小相同的偶数个小块。但是粗心的服务员将披萨切成了每块大小都完全不同奇数块,且肉眼能分辨出大小。 由于两人都想吃到最多的披萨,他们商量了一个他们认…...

uniapp 中video标签视频禁止快,拖拽快进

废话不多说&#xff0c;直接上代码 <video id"myVideo" :src"sectionInfo.type_config.video_url" timeupdate"bindtimeupdate"></video> <script>export default {data() {return {historyTime: 0,}},methods:{// 监听播放进…...

网页端HTML使用MQTTJs订阅RabbitMQ数据

最近在做一个公司的日志组件时有一个问题难住了我。今天问题终于解决了。由于在解决问题中&#xff0c;在网上也查了很多资料都没有一个完整的实例可以参考。所以本着无私分享的目的记录一下完整的解决过程和实例。 需求&#xff1a;做一个统一日志系统可以查看日志列表和一个可…...

课题学习(二十一)----姿态更新的四元数算法推导

声明&#xff1a;本人水平有限&#xff0c;博客可能存在部分错误的地方&#xff0c;请广大读者谅解并向本人反馈错误。    最近需要使用AEKF对姿态进行结算&#xff0c;所以又对四元数进了深入的学习&#xff0c;本篇博客仅对四元数进行推导&#xff0c;后续会对基于四元数的…...

NL2SQL进阶系列(5):论文解读业界前沿方案(DIN-SQL、C3-SQL、DAIL-SQL、SQL-PaLM)、新一代数据集BIRD-SQL解读

NL2SQL进阶系列(5)&#xff1a;论文解读业界前沿方案&#xff08;DIN-SQL、C3-SQL、DAIL-SQL&#xff09;、新一代数据集BIRD-SQL解读 NL2SQL基础系列(1)&#xff1a;业界顶尖排行榜、权威测评数据集及LLM大模型&#xff08;Spider vs BIRD&#xff09;全面对比优劣分析[Text2…...

双指针运用:删除重复元素、移除元素

26.删除重复元素 题目描述 给你一个 非严格递增排列 的数组 nums &#xff0c;请你 原地 删除重复出现的元素&#xff0c;使每个元素 只出现一次 &#xff0c;返回删除后数组的新长度。元素的 相对顺序 应该保持 一致 。然后返回 nums 中唯一元素的个数。 考虑 nums 的唯一元…...

什么是三高架构

三高架构是指在软件系统设计与开发中&#xff0c;注重解决高并发性、高可用性和高性能的架构设计模式。 高并发性&#xff1a;指系统能够处理大量并发请求的能力。在高并发场景下&#xff0c;系统需要具备有效的并发处理机制&#xff0c;以保证系统能够快速、准确地响应大量并…...

Unity 对APK签名

关键代码 PS D:\UnityProject\YueJie> jarsigner -verbose -keystore D:\UnityProject\YueJie\user.keystore -signedjar D:\UnityProject\YueJie\meizuemptyapk-release-signed.apk D:\UnityProject\YueJie\MeizuEmpty-release-unsigned.apk 1 示例 # jarsigner的命令格…...

合成孔径雷达干涉测量InSAR数据处理、地形三维重建、形变信息提取、监测等应用

合成孔径雷达干涉测量&#xff08;Interferometric Synthetic Aperture Radar, InSAR&#xff09;技术作为一种新兴的主动式微波遥感技术&#xff0c;凭借其可以穿过大气层&#xff0c;全天时、全天候获取监测目标的形变信息等特性&#xff0c;已在地表形变监测、DEM生成、滑坡…...

QT进阶------------------QPushButton(快速添加按钮与使用)

1、解决如何快速的添加按钮 在qt中&#xff0c;通常我们喜欢一个按钮添加一个信号与槽&#xff0c;但是这样写太过浪费时间。要是多个按钮那不是要写30个信号与槽&#xff0c;说实话&#xff0c;我不太喜欢这样。 在ui中&#xff0c;只要拖动按钮&#xff0c;会自动生成按钮的名…...

Vue项目管理器创建项目

黑马程序员JavaWeb开发教程 文章目录 1、创建新项目2、详情3、预设4、功能5、配置6、是否保存为预设模板7、正在创建项目8、创建完成 1、创建新项目 2、详情 3、预设 选择手动&#xff0c;点击下一步 4、功能 只需要额外选择一项–Router 即可&#xff0c;其余的保持默认&a…...

PHP-extract变量覆盖

[题目信息]&#xff1a; 题目名称题目难度PHP-extract变量覆盖1 [题目考点]&#xff1a; 变量覆盖指的是用我们自定义的参数值替换程序原有的变量值&#xff0c;一般变量覆盖漏洞需要结合程序的其它功能来实现完整的攻击。 经常导致变量覆盖漏洞场景有&#xff1a;$$&#x…...

研究表明,全球互联网流量竟有一半来自机器人

据Cyber News消息&#xff0c;Thales Imperva Bad Bot近期做了一份报告&#xff0c;显示在2023年有49.6%的互联网流量竟来自机器人&#xff0c;比上一年增长 2%&#xff0c;达到自2013年以来观察到的最高水平。 报告称&#xff0c;这一趋势正对企业组织产生负面影响&#xff0c…...

响应式网站是什么意思/全国免费发布信息平台

转自eoe社区 每一个Tab对应了一个布局&#xff0c;这个就有点好玩了。一个Activity&#xff0c;对应了多个功能布局。①新建一个Tab项目&#xff0c;注意&#xff0c;不要生成main Activity这里不要选②在包里面新建一个类MyTab&#xff0c;继承于TabActivity其实&#xff0c;T…...

南通网站建设知识/网站换了域名怎么查

mysql有个字段是bit&#xff0c;只存储1和0&#xff0c;是二进制存储&#xff0c;那么在java的dao层如何映射成boolean呢 Column(name"is_standard") private boolean isStandard;public void setIsStandard(boolean isStandard){this.isStandard isStandard; }publ…...

网站推广排名怎么做/如何去推广一个app

下面我们来实现Transformer&#xff0c;在正式编写Transformer之前&#xff0c;我们先来看一下实现Transformer的一个小技巧&#xff0c;这个是我们看懂别人写的Transformer代码的一个关键。 1. 数据技巧 还记得我们在讲Transformer原理时&#xff0c;网络层输出z\boldsymbol…...

网站备案流程审核单/谷歌浏览器网页版

前言 这是我第一次参加数学建模比赛&#xff0c;经过和队友几天&#xff08;特别是在辛酸的520日)的通力合作&#xff0c;最终拿了个校奖&#xff0c;其中&#xff0c;由于建模期间同时沉迷于java&#xff0c;建模的语言没有采用建模常用语言matlab&#xff0c;我觉得matlab太不…...

山东淄博网站建设公司/中视频自媒体平台注册官网

代码链接&#xff1a;https://github.com/bgshih/aster 方法概述 本文方法主要解决不规则排列文字的文字识别问题&#xff0c;论文为之前一篇CVPR206的paper&#xff08;Robust Scene Text Recognition with Automatic Rectification&#xff0c;方法简称为RARE&#xff09;的改…...

企业网站的切片怎么做/网站seo诊断分析报告

最近更新的博客 华为od 2023 | 什么是华为od,od 薪资待遇,od机试题清单华为OD机试真题大全,用 Python 解华为机试题 | 机试宝典【华为OD机试】全流程解析+经验分享,题型分享,防作弊指南华为od机试,独家整理 已参加机试人员的实战技巧本篇题解:天然蓄水库 or 天然蓄水池 题…...