第01天 上午01
课程内容
1 初识GO语言 2 开发环境搭建 3 第一个程序(程序结构) 4 基本组成元素:标识符、运算符、分隔符 5 变量、作用域 6 常量、 7 数据类型:布尔型 整数 浮点数 字符串 指针 8 流程控制:if switch for break continue 9 作业:①打印乘法口诀 ②猜数字
001初识GO语言
Go语言发展历史
Go 语言是由谷歌的开发工程师(罗伯特·格瑞史莫、罗勃·派克、肯·汤普逊等)于 2007 年
开始设计,利用 20%的自由时间开发的实验项目,并于 2009 年以 BSD-style 授权(完全开源)首次公开发布,于 2012 年正式发布
开发者使用编程语言的三大分类
执行速度快、 编译速度慢(编译型) C C++
执行速度较慢、编译速度快(解释型) JAVA .NET
执行速度慢、 开发难度小(动态脚本)Python PHP
Go语言是编译型语言:易于开发、快速编译、高效执行
Go语言的优势
+ 1 简单易学 + 25个关键字 + C语言简洁基因,内嵌C语言语法支持 + 面向对象特征(继承, 多态,封装) + 跨平台
+ 2工程化比较优秀 + GoDoc 可以直接从代码和注释生成漂亮的文档 + GoFmt 统一的代码格式 + GoLint 代码语法提示 + 测试框架内置
+ 3 强大的标准库 + Runtime系统调度机制 + 高效的GC垃圾回收 + 丰富的标准库
+ 4 简单的部署方式 + 可直接编译成机械码 + 不依赖其他库 + 直接运行即可部署
+ 5 语言层面的并发 + 天生的基于支持 + 充分利用多核
+ 6 静态类型语言 + 编译的时候可以检测出隐藏的大多数问题 + 强类型方便阅读与重构
+7 垃圾回收 + Go语言的使用者只需要关注内存的申请而不必关心内存的释放, + Go语言内置runtime来自动进行管理
|
+ 包管理, 大部分都在 github上 + 作者修改项目名称 + 作者删库跑路 + vendor 到 mod 迁移麻烦,很多遗留依赖问题
+ 没有Exception,使用Error来处理异常 + error处理不太优雅, 很多重复代码 |
+ 泛型(已经有泛型支持) |
Go语言的应用
应用场景
Go语言主要用于服务端开发,其定位是开发大型软件,常用于: 服务器编程:日志处理、虚拟机处理、文件系统、分布式系统等 网络编程:Web应用、API应用、下载应用等 内存数据库 云平台 机器学习 区块链 ... |
使用Go开发的项目
GO Docker Kubernetes lantern etcd Prometheus Influxdb Consul nsq nats beego ... |
使用Go开发的项目列表
百科 http://github.com/golang/go/wiki 开源项目列表 https://github.com/golang/go/wiki/Projects
编译工具的 Build Tools 缓存的 cache 云计算的 Cloud Computing 命令行工具的 压缩 Compression 并发的 Concurrency and Goroutines 配置的文件解析的 Configuration File Parsers 控制台的 Console User Interface 持续集成 Continuous Integration 加密的 Cryptocurrency 数据处理的 Data Processing 自己实现的一些堆栈等
日期处理 开发工具 文档处理 Email处理
语言机器学习 日志监控
|
使用Go开发的组织
国外 Google Microsoft Amazon FaceBook
国内 阿里 腾讯 百度 京东、爱奇艺、今日头条、滴滴、美团、B站
002开发环境搭建
在线体验
https://golang.google.cn/play/
安装go Windows环境下
下载SDK
官网: https://golang.google.cn/dl/
go中文网:https://studygolang.com/dl
1 默认安装路径 C:\Program Files\Go\bin 2 创建工作目录 D:\GoWork\bin D:\GoWork\pkg D:\GoWork\src
2 配置环境变量 推荐设置 go env -w GO111MODULE=on go env -w GOPROXY=https://goproxy.cn,direct go env -w GOPATH=D:\GoWork
此电脑--属性 -- 高级系统设置 -- 环境变量 3 执行命令 C:\Users\zhu>go version // 查看安装go的版本 go version go1.19.9 windows/amd64 C:\Users\zhu>go env //查看环境 |
安装go Linux环境下
下载SDK
官网: https://golang.google.cn/dl/
go中文网:https://studygolang.com/dl
1 解压到/usr/local目录 tar -xf go1.19.9.linux-amd64.tar.gz -C /usr/local
2 创建工作目录 mkdir -p /root/{bin,pkg,src}
2 配置环境变量 cat > /etc/profile.d/go.sh <<OEF if [[ "x" == "x${GOROOT}" ]]; then export GO111MODULE=on export GOPROXY=https://goproxy.cn,direct export GOROOT=/usr/local/go export GOPATH=${HOME}/go export PATH=${GOROOT}/bin:${GOPATH}/bin:${PATH} fi EOF
source /etc/profile.d/go.sh
3 执行命令 go version go env |
安装Git
先安装git官网: https://git-scm.com/
开发工具
+ Visual Studio code + Sublime Text + Atom + Eclipse+GoClipse + LiteIDE + Goland + Vim + Emacs |
vscode开发环境搭建
vscode官网下载最新版: https://code.visualstudio.com/
1 安装Vscode Go语言插件
插件: Go Golang postfix Outline Map
单词拼写检查: Code Spell Checker 快捷运行代码的插件: Code Runner 最好用Git工具没有之一: Gitlens AI 代码生成: Tabnine AI Code
|
2 安装工具集
设置变量加速 go env -w GOPROXY=https://goproxy.cn,direct 设置变量过后为了保证vscode能正常使用, 请重启vscode
1 打开命令面板: Shift + Ctrl + P 2 输入: Install/Update 搜索 Go扩展依赖工具安装命令
3 勾选所有选项, 点击确认,进行安装
|
安装失败处理
go install -v golang.org/x/tools/gopls@latest go install -v honnef.co/go/tools/cmd/staticcheck@latest go install -v github.com/go-delve/delve/cmd/dlv@latest go install -v github.com/haya14busa/goplay/cmd/goplay@latest go install -v github.com/josharian/impl@latest go install -v github.com/fatih/gomodifytags@latest go install -v github.com/cweill/gotests/gotests@latest go install -v github.com/ramya-rao-a/go-outline@latest go install -v github.com/uudashr/gopkgs/v2/cmd/gopkgs@latest |
3 设置终端使用Git Shell
下载Git https://git-scm.com/downloads 1 Shift + Ctrl + ` 打开终端
2 打开终端的设置界面 3 点击 Git Bash即可
4 重启vscode, 可以看到默认打开Git Bash终端、也可选择其他终端 |
4 配置自动保存
file --> Auto ave 如果要配置自动保存的时间, 打开vscode的设置按钮, 搜索auto save
|
注意:配置完vscode编辑器,需要重启
其他配置参考:用户settings.json
{ "editor.renderWhitespace": "all", //空白渲染 空格会显示 ···· "files.autoSave": "afterDelay", //自动保存 "editor.detectIndentation": false, //检查缩进:false "editor.mouseWheelZoom":true, //鼠标滚轮变焦 true 字体大小 "editor.rulers": [ //显示每行字体数的线 79,89,99 ], "editor.minimap.enabled": false, //右侧文本图:不启用 "files.eol":"\n", //换行符 "files.trimTrailingWhitespace": true, //修改最后空白符 "files.trimFinalNewlines": true, //修改换行符 "workbench.tree.indent": 16, //工作台树缩进 "breadcrumbs.enabled": false, //面包屑 不启用 "editor.suggestSelection": "first", //提示建议值:补全建议值 "go.formatTool":"goimports", // "go.useLanguageServer": true, //自动下载引入包 } |
003第一个程序(程序结构)
注释 //和/* */
D:\GoWork\src\code\day01\helloworld.go
// 定义包main package main // 定义包main
import "fmt" //导入标准包fmt
// 程序入口,main函数 func main(){ /* 我是一个注释 这里调用fmt包下的Println函数打印内容到控制台 */ fmt.Println("Hello world") // 打印hello world到控制台 }
|
go build helloworld.go |
01新建文件helloworld.go,并进行编辑 02 声明包名main 03 导入fmt包 04 定义main函数 05 使用fmt包的Println打印字符串helloworld到控制台 06 编译链接 go build helloworld.go 07 运行 helloworld.exe |
go的几个工具
go build
-x展示编译过程 -o编译生成指定文件 -work 打印临时目录 -n 打印过程不执行 go build helloworld.go go build -x helloworld.go go build -x -o test.exe helloworld.go go build -x -o test.exe -work helloworld.go WORK=C:\Users\zhu\AppData\Local\Temp\go-build3857061314
go run -n helloworld.go |
go run
go run -x helloworld.go
go help
course\day01>go help
go fmt
go fmt helloworld.go
第01天 上午02
004变量&作用域
变量-什么是变变量
给数据起一个名字量
D:\GoWork\src\20220806\course\day01\vars.go
package main
import "fmt"
func main() {
// 变量 给数据起一个名字
var msg string = "hello world"
fmt.Println(msg)
// 其他代码
fmt.Println(msg)
// 其他代码
fmt.Println(msg)
// 其他代码
fmt.Println(msg)
// 其他代码
fmt.Println(msg)
// 其他代码
fmt.Println(msg)
}
变量-作用域
1 包级别,函数级别,块级别,子块级别
D:\GoWork\src\20220806\course\day01\block.go
package main
import "fmt"
// 包级别 var packageVar string = "package Var"
func main() { // 函数级别的 var funcVar string = "func var" { // 块级别 var blockVar string = "block var" { //子块级别 var innerBlockVar string = "inner block var" fmt.Println(packageVar, funcVar, blockVar, innerBlockVar) } fmt.Println(packageVar, funcVar, blockVar) } fmt.Println(packageVar, funcVar) }
|
/* 执行结果: 顺序执行 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run block.go package Var func var block var inner block var package Var func var block var package Var func var */ |
2 父块不能用子级别的变量
package main
import "fmt"
// 包级别 var packageVar string = "package Var"
func main() { // 函数级别的 var funcVar string = "func var" { // 块级别 var blockVar string = "block var" { //子块级别 var innerBlockVar string = "inner block var" fmt.Println(packageVar, funcVar, blockVar, innerBlockVar) } // innerBlockVar 报错 fmt.Println(packageVar, funcVar, blockVar,innerBlockVar) } fmt.Println(packageVar, funcVar) } |
3 先找自己,再找父模块的,没找到再向外找
package main
import "fmt"
// 包级别 var packageVar string = "package Var"
func main() { // 函数级别的 var funcVar string = "func var" var packageVar string = "func package Var" { // 块级别 var packageVar string = "block package Var" fmt.Println(packageVar) } fmt.Println(packageVar, funcVar) } |
/* 打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run block2.go block package Var func package Var func var */ |
4 作用域总结
包packageVar -- {函数级别funcVar -- {块级别 blockVar -- {子块级别 innerBlockVar}}} 1 代码块限定变量使用范围 2 子块可以覆盖父块中定义的变量 |
变量-声明
四种变量声明
1 声明并赋值 var name string = "bob" 2 先声明,后赋值(默认零值)。 var name string 3 不带类型的声明 var name = "bob" 4 短声明(不支持放在函数外) name: = "bob" |
D:\GoWork\src\code\day01\vars2.go
package main
import "fmt"
func main() { // 1声明并赋值 var name string = "bob" // 2 声明不初始化 var zeroString string // 3 声明不指定类型,通过值推导 var typeString = "bob" // 4 短声明(必须在函数内子块中使用) shortString := "bob"
fmt.Println(name, zeroString, typeString, shortString) fmt.Printf("%#v,%#v,%#v,%#v", name, zeroString, typeString, shortString) } |
/* 打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run vars2.go bob bob bob "bob","","bob","bob" */ |
多变量声明() 和 单行声明多变量
D:\GoWork\src\20220806\course\day01\vars3.go
函数外面的可以只声明不使用
package main
import "fmt"
var version = "1.0"
func main() { var ( name string = "bob" msg = "hello world" desc string )
x, y := "x", "y" fmt.Println(name, msg, desc, x, y) } |
/* 打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run vars3.go bob hello world x y */ |
变量-赋值
赋值(更新变量的值)
D:\GoWork\src\code\day01\assign.go
package main
import "fmt"
func main() { var name string = "bob" fmt.Println(name)
name="alice" // 更新变量的值(赋值) fmt.Println(name) } |
/* 打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run assign.go bob alice */ |
块内赋值(不是定义,都更新)
D:\GoWork\src\code\day01\assign1.go
package main
import "fmt"
func main() { var name string = "bob" fmt.Println(name)
name = "alice" // 更新变量的值(赋值) fmt.Println(name) { // 块内定义 name := "dd" fmt.Println(name) } fmt.Println(name) } |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run assign1.go bob alice dd alice */ |
块内定义(仅更新块内)
package main
import "fmt"
func main() { var name string = "bob" fmt.Println(name)
name = "alice" // 更新变量的值(赋值) fmt.Println(name) { // 块内定义 name := "dd" fmt.Println(name) } fmt.Println(name) }
|
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run assign1.go bob alice dd alice */ |
005基本组成元素
标识符
package main
import "fmt"
func main() { /* 标识符:程序中定义的名字 变量名,常量名字,函数名字,自定义类型,接口,包名字 规范: 1. 必须满足:组成只能由非空的Unicode编码字符串、数字、下换线组成 2. 必须满足:必须以Unicode编码的字符串或下换线开头(不能以数字开头) 3. 必须满足:不能与go的关键字冲突(package,func,var... 25个) 建议: 1. AsciII编码(a-z,A-Z)/数字、下划线 2. 变量使用驼峰式 多个英文字母 my_name myName 驼峰 3. 与go内置的标识符不要冲突(string...) 说明:标识符区分大小写 my="" My="" */ var my = "my" var My = "My" var 我的名字 = "bob" // 可以,不建议用 var _myName = "alice" //可以 //var 0Name = "aa" // 不可以 //var package = "bb" // 不可以 fmt.Println(my, My, 我的名字, _myName)
// 关于匿名变量 // var _,b,c = 100,"hello",true } |
运算符
算术运算符 + - * / % ++ -- 逻辑运算符 &&、 ||、 ! 关系运算符 >、 >=、 <、 <=、 ==、 !=
位运算符 &、 |、 ^、 <<、 >>、 &^ 赋值运算符 =、 +=、 -=、*=、 /=、 %=、&=、|=、^=、 <<=、 >>=
其他运算符 &(单目)、 *(单目)、 .(点)、 -(单目)、 ...、 <-
点 变量名.元素 结构体中使用 |
分隔符
小括号() 中括号[] 大括号{} 分号; 逗号, |
第01天 下午01
006常量
声明
声明语句用于定义程序的各种实体对象,主要有:
声明变量的var
声明常量的const
声明函数的func
声明类型的type
常量-声明
常量一旦定义不能修改 常量可以不使用 |
D:\GoWork\src\code\day01\const.go
package main
import "fmt"
func main() { const name string = "bob" fmt.Println(name)
// name = "alice" // 常量一旦定义不能修改
const msg = "msg" // 常量可以不使用
} |
D:\GoWork\src\code\day01\const2.go
package main
import "fmt"
func main() { //const B 不允许 const ( A ="test" B // 使用前一个常量的值进行初始化(B) C // 使用前一个常量的值进行初始化(C=B) D = "testD" E // 使用前一个常量的值进行初始化(D) F // 使用前一个常量的值进行初始化(E=D) ) fmt.Println(B,C) fmt.Println(E,F) } |
枚举类型
D:\GoWork\src\code\day01\enum.go
package main
import ( "fmt" )
func main() { const ( A = iota // 在常量组内使用iota 初始化0, 每次调用+1 B C D ) fmt.Println(A, B, C, D) const ( Mon = iota Tue Wed Thu Fri Sat Sun ) fmt.Println(Mon, Tue, Wed, Thu, Fri, Sat, Sun) }
/* 打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run enum.go 0 1 2 3 0 1 2 3 4 5 6 */ |
打印类型print
D:\GoWork\src\code\day01\print.go
package main
import ( "fmt" "reflect" )
func main() { var name = "bob" fmt.Println("*") fmt.Println(name) //打印变量加换行 fmt.Println("*") fmt.Print(name) // 打印变量不加换行 fmt.Println("*")
fmt.Printf("%T,%v,%#v\n", name, name, name) fmt.Println(reflect.TypeOf(name)) }
|
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run print.go * bob * bob* string,bob,"bob" string */ |
第01天 下午02
007数据类型
布尔类型:用来表示真假 只有两个 真true 假false 数字类型: // 有符号int8 int16 int32(rune) int64 // 无符号uint8(byte) uint16 uint32 uint64 // 平台相关 int uint uintptr 浮点类型 // float32 float64 (非精确的存储) 复数类型 字符串
数组 切片 映射 自定类型 |
布尔类型
声明&零值&占位符%t
D:\GoWork\src\code\day01\bool.go
package main
import "fmt"
func main() { isGirl := false fmt.Printf("%T,%t\n", isGirl, isGirl)
var bbb bool fmt.Printf("%t,%t\n", bbb, "bbb") //零值false,"bbb"是字符串%t提示不匹配 } |
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run bool.go bool,false false,%!t(string=bbb) */ |
逻辑运算
D:\GoWork\src\code\day01\bool1.go
package main
import "fmt"
func main() { // 逻辑运算 a, b, c, d := true, true, false, false fmt.Println("a=true", "b=true", "c=false", "d=false") // 与: 左操作数与右操作数都为true,结果为true && fmt.Println("a&&b:", a && b) fmt.Println("a&&c:", a && c) fmt.Println("c&&b:", c && b) fmt.Println("c&&d:", c && d)
// 或: 左操作数与右操作数只要由一个为true,结果为true || fmt.Println("a=true", "b=true", "c=false", "d=false") fmt.Println("a||b:", a || b) fmt.Println("a||c:", a || c) fmt.Println("c||b:", c || b) fmt.Println("c||d:", c || d)
// 非: 取反 true=> false false=>true ! fmt.Println("a=true", "c=false") fmt.Println("!a:", !a) fmt.Println("!c:", !c)
} |
/* 打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run bool1.go a=true b=true c=false d=false a&&b: true a&&c: false c&&b: false c&&d: false a=true b=true c=false d=false a||b: true a||c: true c||b: true c||d: false a=true c=false !a: false !c: true */ |
关系运算
D:\GoWork\src\code\day01\bool2.go
package main
import "fmt"
func main() { // 关系运算 a, b, c := true, true, false fmt.Println("a=true", "b=true", "c=false") fmt.Println("true==true:", a == b) fmt.Println("true==false:", a == c) fmt.Println("true!=true:", a != b) fmt.Println("true!=false", a != c) } |
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run bool2.go a=true b=true c=false true==true: true true==false: false true!=true: false true!=false true */ |
数字类型:
声明&零值&占位符%d、%b、%o、%x、%X、&默认推断类型int
D:\GoWork\src\code\day01\int.go
package main
import "fmt"
func main() { // 声明 var age8 int8 = 31 // 字面量 10进制 8进制 16进制 var age0 int // 零值 var age = 18 // 默认推断为int型
fmt.Println("字面量 10进制 2进制 8进制 16进制:") fmt.Printf("%T,%d,%b,%o,%x,%X\n\n", age8, age8, age8, age8, age8, age8)
fmt.Println("占位符,格式化对齐:") fmt.Printf("%-8d,\n%8d,\n%08d,\n\n", age8, age8, age8)
fmt.Printf("零值: %T %2d\n", age0, age0) fmt.Printf("推导类型:%T %d\n\n", age, age)
} |
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run int.go 字面量 10进制 2进制 8进制 16进制: int8,31,11111,37,1f,1F
占位符,格式化对齐: 31 , 31, 00000031,
零值: int 0 推导类型:int 18 */ |
1声明:2进制 8进制 16进制数
D:\GoWork\src\code\day01\int1.go
package main
import "fmt"
func main() { // 声明2进制 8进制 16进制数 var v2 int8 = 0b111 var v8 int16 = 070 var v16 int64 = 0x1f fmt.Printf("%T %v\n", v2, v2) fmt.Printf("%T %v\n", v8, v8) fmt.Printf("%T %v\n", v16, v16) } |
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run int1.go int8 7 int16 56 int64 31 */ |
2 算术运算
+ - * / % ++ --
除数不能为0,运行时错误
D:\GoWork\src\code\day01\int2.go
package main
import "fmt"
func main() { // 算术运算 var a, b = 2, 4
fmt.Println(a + b) fmt.Println(a - b) fmt.Println(a * b) fmt.Println(a / b) fmt.Println(a % b)
a++ fmt.Println(a) b-- fmt.Println(b)
// 除0异常 // c, d := 2, 0 //fmt.Println(c / d) //panic: runtime error: integer divide by zero //fmt.Println(c % d) //panic: runtime error: integer divide by zero } |
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run int2.go 6 -2 8 0 2 3 3 */ |
位运算(了解)
了解 D:\GoWork\src\code\day01\int2.go
package main
import "fmt"
func main() {
/* 仅了解 位运算 7 => 0111 2 => 0010
按位与 & 按位或 | 取非 ^ 右移位 >> 左移位 << and not &^ */ fmt.Println("********************************") fmt.Println(7 & 2) fmt.Println(7 | 2) fmt.Println(^2) fmt.Println(7 >> 2) fmt.Println(7 << 2) fmt.Println(7 &^ 2) // 7 & -3 0000 0111 & 1111 1100 转换反码 与0000 0100 fmt.Println(7 & 3) // 7 & 3 0000 0111 & 1000 0011 转换反码 与0000 0011 } |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run int2.go ******************************** 2 7 -3 1 28 5 3 */ |
3 关系运算
D:\GoWork\src\code\day01\int3.go
package main
import "fmt"
func main() { // 关系运算 a, b := 3, 3 fmt.Println(a > b) fmt.Println(a < b) fmt.Println(a == b) fmt.Println(a != b) fmt.Println(a >= b) fmt.Println(a <= b) } |
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run int3.go false false true false true true */ |
fmt.Println(a,b) //3 3
// 关系运算 > < >= <= != ==
fmt.Println(a>b) //false
fmt.Println(a<b) //false
fmt.Println(a>=b) //true
fmt.Println(a<=b) //true
fmt.Println(a==b) //true
fmt.Println(a!=b) //false
}
仅了解
/*
仅了解 位运算
7 => 0111
2 => 0010
按位与 &
按位或 |
取非 ^
右移位 >>
左移位 <<
and not &^
*/
fmt.Println(7&2)
fmt.Println(7|2)
fmt.Println(^2)
fmt.Println(7>>2)
fmt.Println(7<<2)
fmt.Println(7&^2) // 7 & -3
}
4 转换后再计算
D:\GoWork\src\code\day01\int4.go
package main
import "fmt"
func main() { var ( i = 1 i32 int32 = 1 i64 int64 = 1 ) // 类型转换type(value) int32(i) int64(i) int(i32) int(i64) fmt.Println(i + int(i32)) fmt.Println(i + int(i64)) fmt.Println(int32(i) + i32) fmt.Println(int64(i) + i64) } |
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run int4.go 2 2 2 2 */ |
5 字节定义byte、rune&占位%U %c %q &%T打印int32
D:\GoWork\src\code\day01\int5.go
package main
import "fmt"
func main() { var ( achar byte = 'A' aint byte = 65 unicodePoint = '中' ) fmt.Println(achar, aint) fmt.Printf("%T %U %c,%q\n", unicodePoint, unicodePoint, unicodePoint, unicodePoint) fmt.Printf("%d %U %c,%q\n", achar, achar, achar, achar) fmt.Printf("%d %U %c,%q\n", aint, aint, aint, aint) } |
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run int5.go 65 65 int32 U+4E2D 中,'中' 65 U+0041 A,'A' 65 U+0041 A,'A' */ |
6 赋值运算(参考浮点数赋值运算)
浮点数
声明&零值&占位符%f &默认推断类型float64
// float32 float64 (非精确的存储)
D:\GoWork\src\code\day01\float.go
package main
import "fmt"
func main() { var height float32 = 1.68 var heightType = 1.68 //默认类型float64 var width float32 //零值 var k = 1e3 // 1*10^3 fmt.Printf("%T,%#v,%f\n", height, height, height) fmt.Printf("%T,%#v,%f\n", heightType, heightType, heightType) fmt.Printf("%T,%#v,%f\n", width, width, width) fmt.Println(k) } |
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run float.go float32,1.68,1.680000 float64,1.68,1.680000 float32,0,0.000000 1000 */ |
算术运算
D:\GoWork\src\code\day01\float.go
package main
import "fmt"
func main() { var ( f1 = 1.2 f2 = 2.36 ) fmt.Println(f1 + f2) fmt.Println(f1 - f2) fmt.Println(f1 * f2) fmt.Println(f1 / f2)
f1++ f2-- fmt.Print(f1, f2) } |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run float1.go 3.5599999999999996 -1.16 2.832 0.5084745762711864 2.2 1.3599999999999999 */ |
decimal解决精度问题
D:\GoWork\src\code\day01\float2.go
package main
import ( "fmt"
"github.com/shopspring/decimal" )
func main() { var ( a = 1.1 b = 2.34 )
c := decimal.NewFromFloat(a) d := decimal.NewFromFloat(b) //算术运算 fmt.Println(c.Add(d), a+b) fmt.Println(c.Sub(d), a-b) fmt.Println(c.Mul(d), a*b) fmt.Println(c.Div(d).String(), a/b)
fmt.Println("--------------------------------") //float32 与 float64转换 var aa float32 aa = 9.99999 bb := float64(aa) cc := decimal.NewFromFloat32(aa) fmt.Println(bb) fmt.Println(cc.Float64())
} |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run float2.go 3.44 3.44 -1.24 -1.2399999999999998 2.574 2.574 0.4700854700854701 0.47008547008547014 -------------------------------- 9.999990463256836 9.99999 false */ |
关系运算
关系运算 > < >= <= != ==
D:\GoWork\src\code\day01\float3.go
package main
import "fmt"
func main() { // 关系运算 如果想要判断== != 判断差值在一定区间范围内 var ( f1 = 1.2 f2 = 2.36 ) fmt.Println(f1 > f2) fmt.Println(f1 >= f2) fmt.Println(f1 == f2) fmt.Println(f1 != f2)
}
|
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run float3.go false false false true */ |
赋值运算
D:\GoWork\src\code\day01\float4.go
package main
import "fmt"
func main() { //赋值运算 = += -= /= *= var ( f1 = 1.2 f2 = 2.36 ) f1 += f2 fmt.Println(f1) } |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run float4.go 3.5599999999999996 */ |
第01天 下午03
007数据类型
字符串
数组
切片
映射
自定类型
字符串
声明、
D:\GoWork\src\code\day01\string.go
package main
import "fmt"
func main() { var msg ="我的名字\\n是bob" var msgRaw = `我的名字\n是alice` fmt.Printf("%T %s\n",msg,msg) fmt.Printf("%T %s\n",msgRaw,msgRaw) } |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run string.go string 我的名字\n是bob string 我的名字\n是alice */ |
字符串连接+
D:\GoWork\src\code\day01\string1.go
package main
import "fmt"
func main() { var msg = "我的名字\\n是bob" var msgRaw = `我的名字\n是alice` fmt.Println(msg + msgRaw) } |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run string1.go 我的名字\n是bob我的名字\n是alice */ |
关系运算
D:\GoWork\src\code\day01\string2.go
package main
import "fmt"
func main() { // 先比较第一位,再比较第二位 fmt.Println("abc" > "acb") } |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run string2.go false */ |
赋值运算
D:\GoWork\src\code\day01\string3.go
package main
import "fmt"
func main() { var msg ="我的名字是bob" msg+=" -- by bob" fmt.Println(msg) } |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run string3.go 我的名字是bob -- by bob */ |
索引&切片&ascii &字节大小len()
package main
import "fmt"
func main() { msg := "abcdef" var msgRaw = `我的名字\n是TT` fmt.Printf("%T %#v %c\n", msg[0], msg[0], msg[0]) fmt.Println(msg[1:3]) fmt.Println(len(msg)) fmt.Println(len(msgRaw))
} |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run string4.go uint8 0x61 a bc 6 19 */ |
类型转换 - strconv
D:\GoWork\src\code\day01\string5.go
package main
import ( "fmt" "strconv" )
func main() { var ( intVal = 65 float64Val = 2.2 stringVal = "3.3" ) // 整型转浮点,浮点转整型,整型转字符串 fmt.Println(intVal, float64Val, stringVal) fmt.Printf("%T %#v\n", float64(intVal), float64(intVal)) fmt.Printf("%T %#v\n", int(float64Val), int(float64Val)) fmt.Println(string(intVal)) // fmt.Println(string(float64Val)) //cannot convert float64Val (variable of type float64) to stringcompilerInvalidConversion fmt.Println(fmt.Sprintf("%#v\n", float64Val))
// 字符串 <--> 整型(int) fmt.Println(strconv.Itoa(intVal)) v, err := strconv.Atoi(stringVal) fmt.Println(v, err)
// 字符串<--> float64 vv, err := strconv.ParseFloat(stringVal, 64) fmt.Println(vv, err)
fmt.Println(fmt.Sprintf("%#v\n", vv)) fmt.Println(strconv.FormatFloat(vv, 'f', -1, 64)) fmt.Println(strconv.FormatFloat(vv, 'f', -1, 32)) fmt.Println(strconv.FormatFloat(vv, 'f', 10, 64)) fmt.Println(strconv.FormatFloat(vv, 'f', 10, 32))
} |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run string5.go 65 2.2 3.3 float64 65 int 2 A 2.2
65 0 strconv.Atoi: parsing "3.3": invalid syntax 3.3 <nil> 3.3
3.3 3.3 3.3000000000 3.2999999523 */ |
指针类型
声明+new()
*int
D:\GoWork\src\code\day01\pointer.go
package main
import "fmt"
func main() { // 零值 nil var ( pointerInt *int pointString *string ) fmt.Printf("%T %#v\n", pointerInt, pointerInt) fmt.Printf("%T %#v\n", pointString, pointString) pointString=new(string) fmt.Printf("%#v,%#v\n",pointString,*pointString) } |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run pointer.go *int (*int)(nil) *string (*string)(nil) (*string)(0xc000056260),"" */ |
赋值
&name
D:\GoWork\src\code\day01\pointer1.go
package main
import "fmt"
func main() { var pointerInt *int age:=32 fmt.Printf("%T\n", age) pointerInt = &age fmt.Printf("%T\n", pointerInt) fmt.Printf("%v\n", pointerInt) } |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run pointer1.go int *int 0xc00001e0a8 */ |
访问和修改指针
D:\GoWork\src\code\day01\pointer2.go
package main
import "fmt"
func main() { var pointerInt *int age := 32 fmt.Printf("%T\n", age) pointerInt = &age fmt.Println(*pointerInt) *pointerInt = 33 fmt.Println(*pointerInt)
} |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run pointer2.go int 32 33 */ |
复制值变与不变
D:\GoWork\src\code\day01\pointer3.go
package main
import "fmt"
func main() { var pointerInt *int age := 32 age2 := age pointerInt = &age fmt.Println(*pointerInt) *pointerInt = 33 fmt.Println(age, age2)
} |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run pointer3.go 32 33 32 */ |
验证复制地址变量
D:\GoWork\src\code\day01\pointer4.go
package main
import "fmt"
func main() { var pointerInt *int age := 32 age2 := age
pointerInt = &age fmt.Println(&age,&age2,pointerInt) *pointerInt = 33 fmt.Println(&age,&age2,pointerInt)
} |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run pointer4.go 0xc0000a6058 0xc0000a6070 0xc0000a6058 0xc0000a6058 0xc0000a6070 0xc0000a6058 */ |
指针的指针
取地址&name,取值*pointerInt
D:\GoWork\src\code\day01\pointer5.go
package main
import "fmt"
func main() { var ( pointerString *string ) pointerString = new(string) fmt.Printf("%#v,%#v\n", pointerString, *pointerString) pp := &pointerString fmt.Printf("%T\n", pp) **pp = "bob" fmt.Println(*pointerString) fmt.Println(**pp) } |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run pointer5.go (*string)(0xc000058260),"" **string bob bob */ |
scan
输入年龄有误,第一个不能转换为int,会把后边的赋值给下个变量 方式1 用strconv转 方式2 确保输入的为int
|
D:\GoWork\src\code\day01\scan.go
package main
import "fmt"
func main() { name := "" fmt.Print("请输入你的名字:") fmt.Scan(&name) fmt.Println("你输入的名字是:", name)
age := 0 fmt.Print("请输入你的年龄:") fmt.Scan(&age) fmt.Println("你输入的年龄是:", age)
msg := "" fmt.Print("请输入你的msg:") fmt.Scan(&msg) fmt.Println("你输入的msg是:", msg) }
|
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run scan.go 请输入你的名字:bob 你输入的名字是: bob 请输入你的年龄:fds 你输入的年龄是: 0 请输入你的msg:你输入的msg是: ds */
|
008流程控制
if语法
if语法格式
单分支 if 表达式{ 语句体 }
双分支 if 表达式{ 语句体 }else { 语句体 }
多分支 if 表达式{ 语句体 }else if 表达式 { 语句体 }else{ 语句体 }
最后的else不是必须的 |
if语法示例
D:\GoWork\src\code\day01\if.go
package main
import "fmt"
func main() { // 买10个包子 // 如果有卖西瓜的,买一个西瓜 fmt.Println("买10个包子") var y string fmt.Print("有没有卖西瓜的:") fmt.Scan(&y) fmt.Println("你输入的是:", y) if y == "yes" { fmt.Println("买一个西瓜") }
} |
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run if.go 买10个包子 有没有卖西瓜的:yes 你输入的是: yes 买一个西瓜 */ |
if...else...语法示例
D:\GoWork\src\code\day01\if1.go
package main
import "fmt"
func main() { //如果有卖西瓜的买一个包子,否则买10个包子 var y string fmt.Print("有没有卖西瓜的:") fmt.Scan(&y) fmt.Println("你输入的是:", y) if y == "yes" { fmt.Println("买1个包子") } else { fmt.Println("买10个包子") } } |
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run if1.go 有没有卖西瓜的:yes 你输入的是: yes 买1个包子 */ |
if... else if... 语法示例
D:\GoWork\src\code\day01\if2.go
package main
import "fmt"
func main() { //在控制台输入分数 //90及以上A //80及以上B //60及以上C //60及以下D
var score float32 fmt.Print("请输入分数:") fmt.Scan(&score) fmt.Println("你输入的分数是:", score) if score >= 90 { fmt.Println("A") } else if score >= 80{ fmt.Println("B") } else if score >= 60 { fmt.Println("C") } else { fmt.Println("D") } } |
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run if2.go 请输入分数:91.5 你输入的分数是: 91.5 A */ |
switch语法
switch语法格式
只做比对 switch 变量 { case 具体值: 语句A case 值: 语句B case 值: 语句C default: ... }
可以没有default语句块 |
switch语法示例
D:\GoWork\src\code\day01\switch.go
package main
import "fmt"
func main() { //如果有卖西瓜的买一个包子,否则买10个包子 var y string fmt.Print("有没有卖西瓜的:") fmt.Scan(&y) fmt.Println("你输入的是:", y)
switch y { case "yes","y","Y": fmt.Println("买1个包子") case "no","n","N": fmt.Println("买10个包子") default: fmt.Println("输入错误") } } |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run switch.go 有没有卖西瓜的:yes 你输入的是: yes 买1个包子 */ |
D:\GoWork\src\code\day01\switch1.go
package main
import "fmt"
func main() { var score float32 fmt.Print("请输入分数:") fmt.Scanln(&score) fmt.Println("你输入的分数是:", score)
switch { case score >= 90: fmt.Println("A") case score >= 80: fmt.Println("B") case score >= 60: fmt.Println("C") default: fmt.Println("D") } } |
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run switch1.go 请输入分数:90 你输入的分数是: 90 A */ |
if 和 switch 对比:
1、switch比if else更为简洁 2、执行效率更高 3、到底使用哪一个选择语句,代码环境有关,如果是范围取值,则使用if else语句更为快捷;如果是确定取值,则使用switch是更优方案。 |
for循环
循环格式: 四种写法
for 初始值;终止条件;步进 { 循环体 } |
初始值; for 终止条件;{ 循环体 步进 } |
for k,v:=range { 循环体 } |
for { 死循环: } |
打印1-10
D:\GoWork\src\code\day01\for.go
package main
import "fmt"
func main() { // 在控制台打印1...10 for index := 1; index <= 10; index++ { fmt.Println(index) } }
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run for.go 1 2 3 4 5 6 7 8 9 10 */
|
计算1--100和
D:\GoWork\src\code\day01\for1.go
package main
import "fmt"
func main() { // 计算1+2+3+...+100 total:=0 for index := 1; index <= 100; index++ { total += index } fmt.Println(total) }
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run for1.go 5050 */ |
打印1-10(模拟while )
D:\GoWork\src\code\day01\for2.go
package main
import "fmt"
func main() { // 在控制台打印1...10 var index = 1 for index <= 10 { fmt.Println(index) index++ } }
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run for2.go 1 2 3 4 5 6 7 8 9 10 */ |
break
退出循环
D:\GoWork\src\code\day01\break.go
package main
import "fmt"
func main() { for index := 1; index <= 10; index++ { if index == 5 { break // 循环结束 } fmt.Println(index) } }
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run break.go 1 2 3 4 */ |
continue
跳过本次循环,继续下次循环
package main
import "fmt"
func main() { for index := 1; index <= 10; index++ { if index == 5 { continue //跳过本次循环,继续下次循环 } fmt.Println(index) } }
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run continue.go 1 2 3 4 6 7 8 9 10 */ |
遍历--打印每个字符
D:\GoWork\src\code\day01\chars.go
package main
import "fmt"
func main() { letters := "abcdefghi" for i := 0; i < len(letters); i++ { fmt.Println(letters[i]) } }
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run chars.go 97 98 99 100 101 102 103 104 105 */ |
遍历--打印中文
D:\GoWork\src\code\day01\chars1.go
package main
import "fmt"
func main() { letters := "我爱中华人民共和国" for k, v := range letters { fmt.Printf("%T %#v,%T %#v %U ", k, k, v, v, v) fmt.Printf("%q,%c\n", v, v) } }
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run chars1.go int 0,int32 25105 U+6211 '我',我 int 3,int32 29233 U+7231 '爱',爱 int 6,int32 20013 U+4E2D '中',中 int 9,int32 21326 U+534E '华',华 int 12,int32 20154 U+4EBA '人',人 int 15,int32 27665 U+6C11 '民',民 int 18,int32 20849 U+5171 '共',共 int 21,int32 21644 U+548C '和',和 int 24,int32 22269 U+56FD '国',国
*/
|
死循环loop
D:\GoWork\src\code\day01\loop.go
package main
import "fmt"
func main() { var ( index = 0 total = 0 )
for { total += index index++ if index > 100 { break } } fmt.Println(total) }
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run loop.go 5050 */ |
009作业
1. 打印乘法口诀
1 * 1 = 1
2 * 1 = 2 2 * 2 = 4
3 * 1 = 3 3 * 2 = 6 3 * 3 = 9
...
9 * 1 = 9 ... ... 9 * 9 = 81
2. 猜数字游戏
生成随机整数[0, 100)
提示用户再控制台输入猜测的数字
比较,当用户输入较大,提示太大了
当用户输入太小,提示太小了
当用户输入正确,提示经过N次对了,太聪明了
用户最多猜5次,如果5次内都没有猜正确,提示太笨了,游戏结束
3. 扩展: 当成功或失败后,提示用户是否继续,输入:yes, y, Y则继续,重新生成随机数,让用户猜测
1 打印乘法口诀
要求:对齐,
提示:print对齐
D:\GoWork\src\code\day01\homework.go
package main
import "fmt"
func main() { fmt.Printf("%3d]\n", 1) fmt.Printf("%3d]\n", 10000) fmt.Printf("%03d]\n", 1) fmt.Printf("%-0d]\n", 1) } /*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run homework.go 1] 10000] 001] 1] */ |
解答
D:\GoWork\src\code\day01\homework1.go
package main
import "fmt"
func main() { for i := 1; i < 10; i++ { for j := 1; j <= i; j++ { if j == 1 { fmt.Printf("%d*%d=%-2d", j, i, i*j) } else { fmt.Printf("%d*%d=%-2d ", j, i, i*j) } } fmt.Println() } }
/*打印结果 zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run homework1.go 1*1=1 1*2=2 2*2=4 1*3=3 2*3=6 3*3=9 1*4=4 2*4=8 3*4=12 4*4=16 1*5=5 2*5=10 3*5=15 4*5=20 5*5=25 1*6=6 2*6=12 3*6=18 4*6=24 5*6=30 6*6=36 1*7=7 2*7=14 3*7=21 4*7=28 5*7=35 6*7=42 7*7=49 1*8=8 2*8=16 3*8=24 4*8=32 5*8=40 6*8=48 7*8=56 8*8=64 1*9=9 2*9=18 3*9=27 4*9=36 5*9=45 6*9=54 7*9=63 8*9=72 9*9=81 */ |
2 猜数字游戏
提示:生成随机数
D:\GoWork\src\code\day01\homework2.go
package main
import ( "fmt" "math/rand" "time" )
func main() { rand.Seed(time.Now().Unix()) fmt.Println(rand.Intn(10) % 3) // 0-2 fmt.Println(rand.Intn(2)) // [0,2) 不包含2 } |
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run homework2.go 1 0 */ |
解答
D:\GoWork\src\code\day01\homework3.go
package main
import ( "fmt" "math/rand" "time" )
func main() { for { rand.Seed(time.Now().Unix()) num := rand.Intn(101) fmt.Println(num) //fmt.Println(num) var guess int i := 0 for i < 5 { fmt.Print("请输入猜测数字[0-100]:") fmt.Scan(&guess) i++ if guess > num { fmt.Println("猜的太大了,请猜小一点") } else if guess < num { fmt.Println("猜的太小了,请猜大一点") } else if guess == num { fmt.Printf("经过%d次,回答正确,你真棒!\n", i) break } else { fmt.Println("你太笨了,游戏结束!") break } }
var game string fmt.Print("是否继续游戏[yes/no]") fmt.Scan(&game) if game == "yes" { continue } else { break } } }
/*打印结果: zhu@DESKTOP-3LCQABF MINGW64 /d/GoWork/src/code/day01 $ go run homework3.go 66 请输入猜测数字[0-100]:65 猜的太小了,请猜大一点 请输入猜测数字[0-100]:67 猜的太大了,请猜小一点 请输入猜测数字[0-100]:66 经过3次,回答正确,你真棒! 是否继续游戏[yes/no]yes 35 请输入猜测数字[0-100]:35 经过1次,回答正确,你真棒! 是否继续游戏[yes/no]no */
|