go语言之行--基础部分
一、数据类型
布尔型
布尔类型 - 由两个预定义常量组成:true、
false,默认值为false
package mainimport "fmt"func main() {var (a bool //默认值为falseb bool = true)fmt.Println(a,b) }
数字类型
整型:
- uint8(无符号 8 位整型 (0 到 255))
- uint16(无符号 16 位整型 (0 到 65535))
- uint32(无符号 32 位整型 (0 到 4294967295))
- uint64(无符号 64 位整型 (0 到 18446744073709551615))
- int8(带符号 8 位整型 (-128 到 127))
- int16(带符号 16 位整型 (-32768 到 32767))
- int32(带符号 32 位整型 (-2147483648 到 2147483647))
- int64(带符号 64 位整型 (-9223372036854775808 到 9223372036854775807))
浮点型:
- float32(IEEE-754 32位浮点型数)
- float64(IEEE-754 64位浮点型数)
- complex64(复数:32 位实数和虚数)
- complex128(复数:64 位实数和虚数)
其他数字类型:
- byte(字符类型,存储为ascii码,与uint8相同)
- rune(与int32相同)
- uint(32 或 64 位)
- int(与 uint 大小相同)
- uintptr(无符号整型,用于存放一个指针)
字符串类型
表示方式:
- 双引号(" ")
- 反引号(` `)
区别:使用反引号定义的字符串保留原始字符(如换行\n,\t等)会对特殊字符进行转义,打印时候原样输出,而双引号则不转义。
字符串底层是一个byte的数组。
字符串本身是不可变的,因此要改变字符串中的字符,需要将字符串转变为数组,修改数组后再将数组转换为字符串:
package mainimport "fmt"func main() {str := "hello world"s := []byte(str)s[0] = 'W'str = string(s)fmt.Println(str)}//结果 Wello world
双引号、反引号区别:
package mainimport "fmt"func main() {var (a string =`wd\n`b string = "age \n")fmt.Println(a,b) } //结果 wd\n age
派生类型
- 指针类型
- 数组类型
- 结构类型
- 联合类型
- 函数类型
- 切片类型
- 函数类型
- 接口类型
类型转换
不同的数据类型之间是不允许进行赋值或运算操作,必须经过类型转化才能进行运算或者赋值
转换方法:数据类型()
package mainimport "fmt"func main() {var a int32 = 1var b int64 = 64c:= int64(a)+ b //不转换编译报错 fmt.Println(c) }
二、运算符
算数运算符
- +相加 :x + y = z
- -相减 : x - y = z
- *相乘:x * y = z
- % 求余: x % y =z
- ++ 自增 :x++
- -- 自减:x--
关系运算符
- == 判断两个值是否相等,如果相等返回 True 否则返回 False。
- != 判断两个值是否不相等,如果不相等返回 True 否则返回 False。
- > 判断左边值是否大于右边值,如果是返回 True 否则返回 False。
- < 判断左边值是否小于右边值,如果是返回 True 否则返回 False。
- >= 判断左边值是否大于等于右边值,如果是返回 True 否则返回 False。
- <= 判断左边值是否小于等于右边值,如果是返回 True 否则返回 False。
逻辑运算符
- && 逻辑 AND 运算符。 如果两边的操作数都是 True,则条件 True,否则为 False。
- || 逻辑 OR 运算符。 如果两边的操作数有一个 True,则条件 True,否则为 False。
- ! 逻辑 NOT 运算符。 如果条件为 True,则逻辑 NOT 条件 False,否则为 True。
位运算符
位运算符对整数在内存中的二进制位进行操作。
- & 按位与运算符"&"是双目运算符。 其功能是参与运算的两数各对应的二进位相与。
- | 按位或运算符"|"是双目运算符。 其功能是参与运算的两数各对应的二进位相或。
- ^ 按位异或运算符"^"是双目运算符。 其功能是参与运算的两数各对应的二进位相异或,当两对应的二进位相异时,结果为1。
- << 左移运算符"<<"是双目运算符。左移n位就是乘以2的n次方。 其功能把"<<"左边的运算数的各二进位全部左移若干位,由"<<"右边的数指定移动的位数,高位丢弃,低位补0。
- >> 右移运算符">>"是双目运算符。右移n位就是除以2的n次方。 其功能是把">>"左边的运算数的各二进位全部右移若干位,">>"右边的数指定移动的位数。
//假设A = 60, B = 13; 二进制格式表示A = 0011 1100B = 0000 1101-----------------A&B = 0000 1100A|B = 0011 1101A^B = 0011 0001
赋值运算
- = 简单的赋值运算符,将一个表达式的值赋给一个左值
- += 相加后再赋值 (C += A 等于 C = C + A)
- -= 相减后再赋值 (C -= A 等于 C = C - A)
- *= 相乘后再赋值 (C *= A 等于 C = C * A)
- /= 相除后再赋值 (C /= A 等于 C = C / A)
- %= 求余后再赋值 (C %= A 等于 C = C % A)
- <<= 左移后赋值 (C <<= 2 等于 C = C << 2)
- >>= 右移后赋值 (C >>= 2 等于 C = C >> 2)
- &= 按位与后赋值 (C &= 2 等于 C = C & 2)
- ^= 按位异或后赋值 (C ^= 2 等于 C = C ^ 2)
- |= 按位或后赋值 (C |= 2 等于 C = C | 2)
变量运算符
- & 取变量的地址(
&a
将给出变量a
的实际地址) - *取变量的指针(
*a
是指向变量a
的指针)
三、流程控制
if-else
if condition1 { } else if condition2 { //else 一定要和大括号在一行 } else if condition3 { } else { }
for
一般for循环
for i := 0; i < 100; i++ { //语句使用分号隔开 }
死循环(类似python中的while)
for true { } //或者 for { }
使用range遍历数组、slice、map、chan等
package mainimport "fmt"func main() {str := "hell world"for k :=range str { //字符串遍历fmt.Printf("index=%d val=%c len=%d\n",k,str[k],len(str)) //k代表索引、v代表值 }}//结果 index=0 val=h len=10 ....
索引循环
package mainimport "fmt"func main() {str := "hell world"for index,val :=range str { //字符串遍历fmt.Printf("index=%d val=%c len=%d\n",index,val,len(str)) //k代表索引、v代表值 }}//结果 index=0 val=h len=10 ....
同时循环index,val
switch
switch条件控制,当条件匹配当前case时候,执行当前case,不会进行往下执行,若都没有匹配到,则执行default,当然也可以使用fallthrought关键字强制执行下面语句。
switch var { case 条件一: case 条件二: case 条件三: default: }
package mainimport "fmt"func main() {var a = 0switch a {case 0:fmt.Println("this is 0")case 1:fmt.Println("this is 1")case 2:fmt.Println("this is 2")default:fmt.Print("this is default")} }//结果 this is 0
switch 简单示例
package mainimport "fmt"func main() {var a = 0switch { //这里没有变量case a > 0 && a <3: //a in 0-3fmt.Println("a in 0-3")case a < -1 || a > 3:fmt.Println("a <0 or a > 3")case a == 0:fmt.Println("a equal 0")default:fmt.Print("this is default")} //结果 a equal 0 }
多条件判断case
package mainimport "fmt"func main() {var a = 0switch {case a > 0 && a <3: //a in 0-3fmt.Println("a in 0-3")case a < -1 || a > 3:fmt.Println("a <0 or a > 3")case a == 0:fmt.Println("a equal 0")fallthrough //使用fallthrought关键字当满足该条件时候,继续执行下面语句default:fmt.Printf("this is default\n")} //结果 a equal 0 //this is default }
加入fallthrought
goto&label
label作为一个标记,语法是字符串+冒号定义,在循环中使用lable可调至label的定义的位置
package mainimport ("fmt""time" )func main() {LABLE: //定义名称为LABLE//fmt.Println("回到label")for i := 0; i < 10; i++ {fmt.Println("-->",i)for true {i++if i == 6 {time.Sleep(time.Second * 5)break LABLE //跳出循环到LABLE定义的地方 }fmt.Println(i)}}}
goto作用在于跳转到label标签定义的地方继续执行。上述代码修改为goto,将是死循环
package mainimport ("fmt""time" )func main() {LABLE: //定义名称为LABLE//fmt.Println("回到label")for i := 0; i < 10; i++ {fmt.Println("-->",i)for true {i++if i == 6 {time.Sleep(time.Second * 5)goto LABLE //跳出循环到LABLE定义的地方 }fmt.Println(i)}}}//结果:每5秒打印1,2,3,4,5
四、函数
函数是go语言编程的核心。特点:
- 不支持重载,一个包不能有两个名称一样的函数
- 函数也是一种类型,一个函数可以赋值给变量(该特性和python一样)
- 函数也可以不用起名称,这种函数称为匿名函数
- go语言函数可以有多个返回值
- 使用_标识符可忽略返回值
函数定义语法:
func 函数名( 参数 ) [(返回值列表)] {函数体 }// [] 代表非必需
package mainimport ("fmt" )func add(a int,b int) int {return a + b } func main() {c := addd := c(1,2) // 加括号代表调用函数 fmt.Println(d)}//结果:3
函数作为变量demo
package mainimport ("fmt" )func add(a int,b int) (int,int) {return a + b,a } func main() {c := addd , _ := c(1,2) //使用_忽略第二个返回值 fmt.Println(d)}//结果:3
忽略返回值demo
函数参数传递方式
值传递:一般基本的数据类型都是值传递,如数字、字符串。
引用传递:复杂的数据类型,如map、chan、interface,是引用传递。
注意:无论是值传递还是引用传递,传递给函数的都是变量的副本,不过值传递是值的拷贝,引用传递拷贝的是地址,一般来说地址拷贝更为高效。而值拷贝取决于拷贝对象大小,对象越大,则性能相对低。
函数返回值命名
go 函数的返回值或者结果参数可以指定一个名字(名字不是强制的),并且像原始的变量那样使用,就像输入参数那样。如果对其命名,在函数开始时,它们会用其类型的零值初始化;如果函数在不加参数的情况下执行了 return
语句,结果参数的当前值会作为返回值返回。
package mainimport "fmt" //斐波那契数列实现 func Factorial(x int) (result int) { //给函数返回值命名为resultif x <= 1 {result = 1} else {result =Factorial(x - 2) + Factorial(x - 1)}return } func main() {b := Factorial(4)fmt.Println(b)}//结果:5
匿名函数
匿名函数(对比javascript)即没有函数名的函数,只能放在函数中,可以实现函数嵌套定义的功能。
package mainimport "fmt"func main() {c := func(a int,b int ) int {return a + b}(3,4)fmt.Println(c)}//结果:7
函数的可变参数
go语言中,也可以像python一样传递可变参数(意思是传递时候才确定有几个参数,定义时候不知道参数个数),可以认为参数是数组形式:
func funcname(arg...type) { }
package mainimport "fmt"func add(a int, arg...int) int {var sum = 0for i := 0; i < len(arg); i++ {sum += arg[i] //取参数的值 }return sum } func main() {c := add(1) //传递一个参数d := add(2,3,4) //传递两个参数 fmt.Println(c,d)}//结果:0,7
defer
当函数中存在defer关键字时候,一旦函数返回则执行defer语句,因此,defer可以做一些资源清理的事情。
特性:
- 多个defer语句,按照后进先出的方式执行。
- defer语句中的变量,在defer声明时候就决定了。
package mainimport "fmt"func main() {i := 0defer fmt.Println(i) // 放入栈i++defer fmt.Println(i) //在放入栈,先执行fmt.Println("wd")return}//结果:wd ,1,0
命令行参数
概念:
- 命令行参数(或参数):是指运行程序时提供的参数。
- 已定义命令行参数:是指程序中通过
flag.Xxx
等这种形式定义了的参数。输入参数时需要-flag
形式。 - 非 flag(non-flag)命令行参数(或保留的命令行参数):不符合
-flag
形式的参数。-
、--
和--flag
都属于 non-flag 参数。
来自命令行的参数在程序中通过os.Args(对比python的sys.agrv)
获取,导入包 os 即可。其中 os.Args[0]
为执行的程序名,os.Args[1]
~ os.Args[n-1]
是具体的参数。
//示例 test.exe 1 2 //test.exe 为os.Args[0] ,1是 os.Args[1],2是os.Args[2]
go语言的初始化顺序
初始化顺序规则: 引入的包 -->包中的常量、变量、init-->当前包的常量、变量、init -->main函数
图示:
注意事项:
- 当前go源文件中, 每一个被Import的包, 按其在源文件中出现顺序初始化。
- 如果当前包有多个init在不同的源文件中, 则按源文件名以字典序从小到大排序,小的先被执行到, 同一包且同一源文件中的init,则按其出现在文件中的先后顺序依次初始化; 当前包的package level变量常量也遵循这个规则; 其实准确来说,应是按提交给编译器的源文件名顺序为准,只是在提交编译器之前, go命令行工具对源文件名按字典序排序了。
- init只可以由go runtine自已调用, 我们在代码中不可以显示调用,也不可以被引用,如赋给a function variable。
- 包A 引入包B , 包B又引入包C, 则包的初始化顺序为: C -> B -> A
- 引入包,必须避免死循环,如 A 引 B , B引C, C引A.
- 一个包被其它多个包引入,如A -> B ->C 和 H -> I -> C , C被其它包引了2次, 但是注意包C只被初始化一次。
- 另一个大原则, 被依赖的总是先被初始化,main包总是被最后一个初始化,因为它总是依赖别的包。
转载于:https://www.cnblogs.com/wdliu/p/9183267.html
go语言之行--基础部分相关推荐
- 语言的学习基础,100个经典的算法
POJ上做做ACM的题 语言的学习基础,100个经典的算法 C语言的学习要从基础开始,这里是100个经典的算法-1C语言的学习要从基础开始,这里是100个经典的算法 题目:古典问题:有一对兔子,从出生 ...
- 经济专业需要学c语言吗,学c语言要什么基础?
. C语言是应用非常广泛的计算机编程语言,一直被想从事IT行业的伙伴们认为是必须学习的课程.那么,学习C语言需要哪些基础?接下来,编辑将简要介绍它.. 学习C语言需要什么基础?零基础学习c语言时,首先 ...
- 【Java开发语言 01】第一章 Java语言概述(基础常识+Java语言概述+Java程序运行机制及运行过程+Java语言环境的搭建+开发体验hello world+错误:编码GBK的不可映射字符)
java入门-第一章Java语言概述 1基础常识 软件开发 人机交互方式 常用的DOS命令(win系统,有一些直接通过命令执行的) 2 Java语言概述 什么是计算机语言 关于面向对象和面向过程 Ja ...
- R语言命令行写linux,如何在Linux上编写和使用R脚本
--by不是杀杀 虽然大多数时候在Windows下和在Jupyter中能够非常方便快捷地进行R语言编程,但对于处理数据量较大的工作时,还是避免不了需要在服务器上运行我们写的代码,那么我们要如何方便快捷 ...
- golang语言的入门基础,及window和linux系统上环境的搭配及运行
golang语言的入门基础,及window和linux系统上环境的搭配及运行 简介: Go语言是谷歌推出的一种全新的编程语言,可以在不损失应用程序性能的情况下降低代码的复杂性.Go语言专门针对多处理器 ...
- python语言的变量类型_Python语言变量类型基础学习
本文主要向大家介绍了Python语言变量类型基础学习,通过具体的内容向大家展示,希望对大家学习Python语言有所帮助. Python基本语法1.定义常量: 之前定义变量没有一起介绍定义常量,是因为P ...
- C语言与C++基础编写贪吃蛇项目1
C语言与C++基础编写贪吃蛇项目1 第一阶段: 简单的移动的贪吃蛇编写. 小白编写,勿喷. 一.总体项目功能: 1.添加背景音乐或者动作音效 2.有欢迎界面,游戏选项等界面 3.地图范围内有障碍物,可 ...
- C语言100行代码实现推箱子
1 C语言100行代码实现推箱子 1.1 概述 C语言是很好入门编程的一个语言,它拥有着很好的移植性,基本上所有的平台都支持C语言编程.有些C语言基础的你,是不是也很想做一个项目来检验一下自己的学习 ...
- C语言中重要基础知识的概述
本章主要对于C语言中的基础知识进行一个大致的描述,适合有C语言基础但长久没接触C语言开发的人员进行快速回忆.在总体回忆基础知识之前,先来创建一个C程序.笔者的编译器是visual stduio2013 ...
最新文章
- 单卡手机怎么变双卡双待全过程
- Generation Language GL
- python email模块详解_python模块之email: 电子邮件编码解码 (一、解码邮件)-阿里云开发者社区...
- linux zlib简介
- Selenium Webdriver原理终于搞清楚了
- 第九届蓝桥杯java B组—第六题递增三元组(详细介绍)
- Uncaught TypeError: Object #Document has no method 'load'
- 电脑账户头像怎么删掉_情侣头像丨情侣头像一男一女背影
- java list按照元素对象的指定多个字段属性进行排序
- Machine learning for improved image-based wavefront sensing
- (转载)Box2D v2.3.0 用户手册中文版(第1章)-导言
- HttpClient模拟登陆并获取指定页面的内容
- 【Python】如何实现列表的升序排列
- Android 高德地图的开发
- Kerberos协议简介
- 医疗设备维修保养及常见故障维修技术学习
- windows装机必备:文件查找神器Everything + Wox
- lamp 架构的搭建
- 【keras】keras教程(参考官方文档)
- 腾讯游戏学院------SLG游戏技术【笔记】
热门文章
- python读取csv文件并修改指定内容-pandas读取CSV文件时查看修改各列的数据类型格式...
- python变量类型-Python 变量类型详解
- python发明者叫什么-python是谁的
- python入门买什么书-关于 Python 的经典入门书籍有哪些?
- python个人赚钱攻略-每个懂Python的人都必须知道的赚钱神器
- 廖雪峰python教程百度云-廖雪峰Python教程的配套视频教程,全套完整版!
- 学python工资高吗-Python工资一般是多少 看完吓你一跳
- python新手入门教程-终于知晓python新手练习教程
- 零基础学编程学java还是python-零基础学编程,Java和Python你pick谁?
- 初学python还是swift-iOS 将来 Swift 也许会取代 Python