壹影博客.
我在下午4点钟开始想你
零基础快速入门系列-Golang基础入门
  • 2024-8-4日
  • 0评论
  • 999围观

零基础快速入门系列-Golang基础入门

  Golang官网:https://go.dev/

一、注释 &打印

//主函数
func main(){
  //打印方式
  fmt.Println(内容)
}

// 单行注释
/**
  多行注释
**/

 二、 数据类型

 Golang  基本数据类型包括如下

1.有符号整型 int:正整数、负整数、0 
2.无符号整型 uint:正整数、0
3.浮点型 float32:精确到小数点后7位
4.   浮点型 float64(常用):精确到小数点后15位
5.布尔类型 bool:ture、false 
6.字符类型 byte: var ch byte = 'A'
7.字符串 :var str string = "张三"

var a int = -20 //int
var b uint = 20 //uint
var c float32 = 5.6 //float32
var d float64 = 3.141596 //float64
var e bool = ture //bool
var f byte = 'A' //byte
var g string = "张三" //string

三、变量申明与使用

1. var  普通变量
2.const 常量

var b int = 100 //全局变量
const PI float64 = 3.14 //常量 不可变的变量

func main(){
    var a int = 50  //变量a只在main函数中有效 这个是局部变量
    c:=75 //另一种变量定义的方式:= 
    fmt.Println(c) //打印c ==>75
}

func test(){
    fmt.Println(a) //会报错,因为a是局部变量
}

四、逻辑&分支

逻辑运算
  1.  == 等于
  2. != 不等于
  3. > 大于
  4. >= 大于且等于
  5. < 小于
  6. <= 小于且等于
  7.  && 逻辑 And
  8. || 逻辑Or
  9. ! 逻辑 非

逻辑分支
  1.if..else
  2.if..else...if
  3.switch

var age int = 18
//if else
if age>18 {
    fmt.Println("已成年!!")
}else{
    fmt.Println("未成年!!")
}

//switch
switch{
  case age>18:
   fmt.Println("已成年!!")
  case age<18 && age>0:
   fmt.Println("未成年!!")
  case age==18:
   fmt.Println("刚好成年!!")
  default:
   fmt.Println("参数不合法!!")
}

五、循环遍历

1.  普通for
2.  for..range

for i := 1; i <= 10; i++ {
    if i==8{
      break //退出大循环
    }
    if i==5{
      continue //退出本轮循环
    }
    fmt.Printf("这是多少 %d \n", i)
}

// for range 循环
for k,v:=range data {
  ...
}

// 死循环
for{
  ...
}

六、函数定义与使用

1. 普通 函数
2. 不定参函数

//普通函数定义:第一种
func xxxx(参数名 类型) int {
    //do...
    return xxxx
}

//普通函数定义:第二种 这种方式会在方法内部帮我们创建虚sum 不需要手动var
func xxxx(参数名 类型) (sum int) {
    //do...
    return //由于在声明处已标名 返回sum 则return处不需要写sum
}

//多个返回参数
func xxxx(参数名 类型) (int,int) {
    //do...
    return xxxx,xxxxx
}

//不订参函数定义
func sum(args ...int) int {
	for k, v := range args {
		fmt.Printf("k=%d,v=%d \n", k, v)
	}
     return xxxx
}
func main() {
    //函数调用
	sum(1, 3, 5, 7, 9, 10)
}

七、数组的使用

1.数组的定义&使用
2.函数与数组

 注意: Golang 中下标 以0开始

//定义一个数组
var nums[5] int =  [5] int {1,2,3,4,5} //下标从0开始
nums2:=[...] int {5,6,7} //定义不定长数组
fmt.Println(nums2[0]) //输出:5

//数组做为函数参数
//主函数
func main() {
	arr:=[5]int{2,5,3,4,8}
	numArr(arr)
}
//测试参数 数组作为函数参数
func numArr(arr[5] int) (index int){
	index = arr[0]
    return index
}

八、切片

描述:切片与数组相比切片的长度是不固定的,可以追加元素,在追加时可能使切片的容量增大所以可以将切片理解成“动态数组”,但是,它不是数组。切片则使用得相当广泛

1.定义与初始化
2. 遍历
3. 截取

// 定义与初始化

// 方式一
var split[] int
split = append(split,1,2,3,4,5)

//方式二
split:=[] int{}
split = append(split,1,2,3,4,5)

//方式三
split:=make([]int,3,10)
split = append(split,1,2,3)
// len()函数返回长度,cap()返回容量
// make()函数中的容量参数是可以省略掉的,这时容量与长度是相等的。
// 2.遍历

// for...len()
var split[] int
split = append(split,1,2,3,4,5)
for i:=0,i<len(split),i++ {
    fmt.Println(split[i])
}

// for..range
var split[] int
split = append(split,1,2,3,4,5)
for k,v:=range split {
    fmt.Println(k)
    fmt.Println(v)
}
// 3.截取
var split[] int
split = append(split,1,2,3,4,5)
//第一个值:从下标为0的位置开始截取
//第二个值:终止位置的下标,不包含该值
//第三个值:容量,最多可容纳多少个元素
s1:=split[0:3:5] 

// 示例
var split []int
split = append(split, 1, 2, 3, 4, 5)
//第一个值:从下标为0的位置开始截取
//第二个值:终止位置的下标,不包含该值
//第三个值:容量,最多可容纳多少个元素
s1 := split[3:]
fmt.Println(s1) //4,5  从下标为3的位置开始截取 到最后长度

注意:扩容 切片扩容为2倍扩容

九、Map的使用

1.创建与初始化
2. 判断 Key 是否 存在
3. 删除 key

// 定义与初始化Map
m := map[int]string{1: "张三", 2: "李四", 3: "王五"}
m[1] = "hello map"
m1 := map[string]string{"key1": "张三", "key2": "李四", "key3": "王五"}
m1["key1"] = "你好 map"
fmt.Println(m) //[1:hello map 2:李四 3:王五]
fmt.Println(m1) //[key1:你好 map key2:李四 key3:王五]
//也可以通过make函数创建map

//判断判断键知否存在
m := map[string]string{"key1": "张三", "key2": "李四", "key3": "王五"}
m["key1"] = "你好 map"
key, value := m["mmm"] //取一个不存在的值
fmt.Println(key, value)
if value == false {
    fmt.Println("不存在的key")
}

//删除Key  delete
m := map[string]string{"key1": "张三", "key2": "李四", "key3": "王五"}
delete(m, "key1")
fmt.Println(m)

十、结构体

结构体是由一系列具有相同类型或不同类型的数据构成的数据集合,结构体可以很好地管理一批有联系的数据,使用结构体可以提高程序的易读性

1.创建与初始化
2. 结构体与切片

// 定义一个结构体
type Student struct {
    name     string //名称
    age      int    //年龄
    classNum int    //班级
    sex      string //性别
    nick     string //昵称
}
//初始化结构体
var stu Student = Student{"张三", 18, 5, "男", "法外狂徒"}

//部分初始化
var stu2 Student = Student{name: "张三", sex: "男", nick: "法外狂徒"}
fmt.Println(stu) //{张三 18 5 男 法外狂徒}
fmt.Println(stu2) //{张三 0 0 男 法外狂徒}
//切片与结构体 结合使用
type Student struct {
    name     string //名称
    age      int    //年龄
    classNum int    //班级
    sex      string //性别
    nick     string //昵称
}

func main() {
    var s = []Student{
        {"张三", 18, 5, "男", "法外狂徒"},
        {"李四", 25, 6, "女", "轻狂莫嚣张"},
        {"王五", 20, 4, "男", "脸上有麻子"},
    }
    fmt.Println(s) //[{张三 18 5 男 法外狂徒} {李四 25 6 女 轻狂莫嚣张} {王五 20 4 男 脸上有麻子}]
}

十一、指针

指针也是个变量,但它是一种特殊的变量因为它存储的数据不仅仅是一个普通的值,如简单的整数或字符串,而是另一个变量的内存地址。

1.指针定义与使用

funv main(){
    var a int = 10 
    var p *int //指针变量
    p = &a //赋值a的内存地址
    fmt.Printf("%p\n",&a) //0xc00000a0b8
    fmt.Printf("%p",p) //0xc00000a0b8

    fmt.Println(*p) //*p根据内存地址取值 10
    *p = 222 //修改内存地址的值
    fmt.Println(*p) //*p根据内存地址取值 222

    //指针参数示例
	num := 10
	add(&num) //传入内存地址
	fmt.Println(num)
}


//传入内存地址在指针
func add(num *int) {
	*num++  //指针取值++
}

十二、协程

描述:Golang协程又叫Goroutine是与其他函数或方法同时运行的函数或方法。Goroutines可以被认为是轻量级的线程。与线程相比,创建Goroutine的成本很小它就是一段代码,一个函数入口。以及在堆上为其分配的一个堆栈(初始大小为4K,会随着程序的执行自动增长删除)。因此它非常廉价,G0应用程序可以轻松并发运行数千个Goroutines

1. 基本 使用
2. 协程加锁
3. 同步等待组

//协程基本使用
// 协程测试
func main() {
	go goroutine() //开启协程 方式1 用go关键字
	go func() {    //方式2 匿名函数
		fmt.Println("协程方法测试 匿名函数")
	}()
	time.Sleep(time.Second * 2) //睡眠3秒
	fmt.Println("主线程")
}

func goroutine() int {
	fmt.Println("协程方法测试")
	return 123
}
/**
    输出结果
    协程方法测试
    协程方法测试 匿名函数
    主线程
**/
// 加锁示例

//需求:假如有十张票 有三个售票机同时售票利用锁机制解决数据安全性问题
// 设置10张票
var ticket int = 10

// 定义锁头 Mutex
var mutex sync.Mutex

// 协程终止测试
func main() {
	//开两个协程同事卖票
	go TicketSale("1号") //第一个售票机
	go TicketSale("2号") //第一个售票机
	go TicketSale("3号") //第一个售票机

	time.Sleep(time.Second * 10)
	//查看卖票结果
	fmt.Println("当前票:", ticket)
}

func TicketSale(name string) {
	for { //模拟售票机 有票就会售票
		mutex.Lock() // 加锁 上厕所关门
		if ticket > 0 {
			fmt.Printf("%s售票机 售出第%d号票\n", name, ticket)
			ticket--
		} else {
			//当票等于0时结束
			mutex.Unlock() //解锁 上完厕所开门
			break
		}
		mutex.Unlock() //解锁 上完厕所开门
	}
}

//主要代码
//var mutex sync.Mutex //定义锁
//mutex.Lock()  //加锁
//mutex.Unlock()  //解锁
// 同步等待组 waitgroup
// 定义同步组
var wt sync.WaitGroup

// 协程终止测试
func main() {
	wt.Add(2) //开两个协程
	//开两个协程
	go group("group1")
	go group("group2")

	//上面两个协程结束后自动停止 而不是手动设置固定在睡眠时间
	// time.Sleep(time.Second * 10)
	wt.Wait() //等待
	fmt.Println("main end...")
}
func group(name string) {
	go func() {
		for i := 0; i < 5; i++ {
			fmt.Printf("%s i=%d \n", name, i)
		}
		wt.Done() //消费同步组 变量
	}()
}

 

发表评论

渝ICP备19011465号 | 渝ICP备19011465号-1