前言
本人是一个普通的java后端开发,借此机会系统的学习go语言,其实是看上奖品了,所涉及的知识会根据书籍《Go语言编程》学习并总结打卡,在此先感谢Go语言编程的团队,后面文章不做特别备注!
语言简史
贝尔实验室从20世界80年代开始的一个名为Plan 9的操作系统的研究项目,起初的目的是解决Unix中出现的问题,经过发展项目演变成一个叫Inferno的项目分支,以及一个名为Limbo的编程语言。Limbo是运用于小型计算机上的分布式应用编程语言,支持模块化编程,编译期间和运行期间支持强类型检查。被设计为在没有硬件内存保护的小型设备上也能安全运行。后来贝尔实验室做Plan 9项目的原班人员加入Google。在Google他们创建了Go语言。还有Go语言的命名是基于引入了java中废弃的go关键字呢,还是开发公司是Google而命名就不得而知!!!!
语言特性
自动回收垃圾
- C语言 C语言不支持自动回收,需要程序员手动回收,如果由于疏忽没有手动书写回收代码,在频繁调用的情况下会导致系统程序奔溃。手动管理内存的另外一个问题就是指针到处传递而无法确定何时可以释放该指针指向的内存块,有些指针释放了,但其他地方用到该指针指向的内存区域,那么这些指针会变成“野指针”(wild pointer)或者悬空指针(dangling pointer),对这种指针很难去处理怎么回收。
- java java有自己的自动垃圾回收机制,和垃圾清理算法,为了确认哪些引用垃圾可以回收,引入了引用计数器,和GC_Root的可达性算法,针对垃圾收集算法,引入了复制算法,标记整理算法,和分代收集算法等。总的来说java的垃圾回收是自动回收,确认和回收比较复杂。
- go 自带垃圾回收机制,没有c语言的复杂的指针,不需要程序员手动回收,系统cpu会选择在空闲的时候自动回收,我姑且认为会自动回收,而且算法简单,不用程序员操心。
更丰富的内置类型
- 支持常用的内置类型(比如整型浮点型),支持字典型map类型,go语言设计者认为绝大多数开发者都需要这个类型,那么我就支持,新增的数据类型:数组切片:对比java我认为是一种可以动态增长的的数组,有点像java的ArrayList会动态扩容。
函数多返回值
- 相对于java的函数想返回多个值,一般的做法是把返回值封装到一个对象里面,这个对象里面有多个属性对应多个值,或者用一个数组分别放多个值。
- go语言多个返回值举例:
func getName()(firstName, middleName, lastName, nickName string){
return "雷", "小", "鸿", "H"
}
或者
func getName()(firstName, middleName, lastName, nickName string){
firstName = "雷"
middleName = "小"
lastName = "鸿"
nickName = "H"
return
}
错误处理
- Go语言引入了三个关键字来处理标准的错误流程,分别为:defer、panic和recover和java的捕获异常相比,Go语言的错误处理机制用更少的代码量来处理,避免了如果java处理异常的try-catch语句块,这点java中很多的try-catch语句块极大的影响了代码的美感。
匿名函数和闭包
- 在Go语言中,所有的函数也是值类型,可以作为参数传递。Go语言支持常规的匿名函数和闭包
类型和接口
- go语言的接口非常接近c语言的struct,甚至直接沿用了struct关键字,相对于java不支持继承和重载,只是支持最基本的组合,也不用遵循实现了接口,接口的修改会影响了所有实现该接口的实现类,go语言的接口避免了这种问题。这点需要用到再理解。
并发编程
- Go语言引入了goroutine概念,通过使用goroutine而不是直接用操作系统的并发机制,用消息传递来共享内存,而不是直接使用内存来通信,简而言之并发编程更加的轻盈和安全。具体的是通过在函数调用前使用关键字go,简而言之goroutine是一种比线程更加轻盈更加省资源的协程。go语言通过系统的线程来多路派遣这些函数的执行,而且cpu可以在多个goroutine之间切换,cpu可以很容易的创建大量的goroutine从而轻松的编写高并发的程序,goroutine之间的通信顺序进程,我的理解有点像java的程序计数器是各个线程私有的,保证线程切换回去能找到原来离开的位置继续执行,进程之间通过通信顺序进程来实现跨goroutine的通信。
反射
- 反射:在程序运行期间动态的去获取对象的的详细信息,并可以操作对象,java可以通过静态方法Class.forName,引用对象.getClass, 类名.class来使用。go语言实现了基于java的反射的大部分功能,但是没有java语言那样内置型工厂,无法通过类型字符串来创建对象实例,java中你可以读取配置并根据类型名称创建对应的类型,这是一种常见的编程手法。go语言则不行,go语言使用的常见场景是做对象的序列化。
语言交互性
- 由于Go语言与C语言之间的天生联系,Go语言的设计者们自然不会忽略如何重用现有C模块的这个问题,这个功能直接被命名为Cgo。Cgo既是语言特性,同时也是一个工具的名称,这点有点像java的本地方法栈通过JNI直接调用本地C/C++库。
备注
本文正在参与「掘金Golang主题学习月」, 点击查看活动详情