mirror of
https://github.com/gopl-zh/gopl-zh.github.com.git
synced 2024-11-24 07:14:47 +00:00
Compare commits
4 Commits
24b5b44e03
...
c12f1dbf53
Author | SHA1 | Date | |
---|---|---|---|
|
c12f1dbf53 | ||
|
410eae5257 | ||
|
cf65b5d7d8 | ||
|
dd9495c90d |
@ -166,6 +166,7 @@
|
||||
<p><img src="cover.jpg" alt="" /></p>
|
||||
<ul>
|
||||
<li>在线阅读:<a href="https://gopl-zh.github.io">https://gopl-zh.github.io</a></li>
|
||||
<li>在线阅读:<a href="https://golang-china.github.io/gopl-zh">https://golang-china.github.io/gopl-zh</a></li>
|
||||
<li>项目主页:<a href="https://github.com/gopl-zh">https://github.com/gopl-zh</a></li>
|
||||
<li>项目主页(旧):<a href="http://github.com/golang-china/gopl-zh">http://github.com/golang-china/gopl-zh</a></li>
|
||||
<li>原版官网:<a href="http://gopl.io">http://gopl.io</a></li>
|
||||
@ -176,6 +177,11 @@
|
||||
<li>译者:Xargin, <a href="https://github.com/cch123">https://github.com/cch123</a></li>
|
||||
<li>译者:CrazySssst, <a href="https://github.com/CrazySssst">https://github.com/CrazySssst</a></li>
|
||||
<li>译者:foreversmart, <a href="https://github.com/foreversmart">https://github.com/foreversmart</a> <a href="mailto:njutree@gmail.com">njutree@gmail.com</a></li>
|
||||
</ul>
|
||||
<p>Go 语言中国:</p>
|
||||
<ul>
|
||||
<li>Go 语言中国:<a href="https://github.com/golang-china">https://github.com/golang-china</a></li>
|
||||
<li>Go 语言中国论坛:<a href="https://github.com/golang-china/main.go/discussions">https://github.com/golang-china/main.go/discussions</a></li>
|
||||
</ul>
|
||||
|
||||
|
||||
|
16
preface.html
16
preface.html
@ -166,19 +166,19 @@
|
||||
<p>编程语言的演化跟生物物种的演化类似,一个成功的编程语言的后代一般都会继承它们祖先的优点;当然有时多种语言杂合也可能会产生令人惊讶的特性;还有一些激进的新特性可能并没有先例。通过观察这些影响,我们可以学到为什么一门语言是这样子的,它已经适应了怎样的环境。</p>
|
||||
<p>下图展示了有哪些早期的编程语言对Go语言的设计产生了重要影响。</p>
|
||||
<p><img src="../images/ch0-01.png" alt="" /></p>
|
||||
<p>Go语言有时候被描述为“C类似语言”,或者是“21世纪的C语言”。Go从C语言继承了相似的表达式语法、控制流结构、基础数据类型、调用参数传值、指针等很多思想,还有C语言一直所看中的编译后机器码的运行效率以及和现有操作系统的无缝适配。</p>
|
||||
<p>但是在Go语言的家族树中还有其它的祖先。其中一个有影响力的分支来自<a href="https://en.wikipedia.org/wiki/Niklaus_Wirth">Niklaus Wirth</a>所设计的[Pascal][Pascal]语言。然后[Modula-2][Modula-2]语言激发了包的概念。然后[Oberon][Oberon]语言摒弃了模块接口文件和模块实现文件之间的区别。第二代的[Oberon-2][Oberon-2]语言直接影响了包的导入和声明的语法,还有[Oberon][Oberon]语言的面向对象特性所提供的方法的声明语法等。</p>
|
||||
<p>Go语言的另一支祖先,带来了Go语言区别其他语言的重要特性,灵感来自于贝尔实验室的<a href="https://en.wikipedia.org/wiki/Tony_Hoare">Tony Hoare</a>于1978年发表的鲜为外界所知的关于并发研究的基础文献 <em>顺序通信进程</em> ( <em>[communicating sequential processes][CSP]</em> ,缩写为[CSP][CSP]。在[CSP][CSP]中,程序是一组中间没有共享状态的平行运行的处理过程,它们之间使用管道进行通信和控制同步。不过<a href="https://en.wikipedia.org/wiki/Tony_Hoare">Tony Hoare</a>的[CSP][CSP]只是一个用于描述并发性基本概念的描述语言,并不是一个可以编写可执行程序的通用编程语言。</p>
|
||||
<p>接下来,Rob Pike和其他人开始不断尝试将<a href="https://en.wikipedia.org/wiki/Communicating_sequential_processes">CSP</a>引入实际的编程语言中。他们第一次尝试引入<a href="https://en.wikipedia.org/wiki/Communicating_sequential_processes">CSP</a>特性的编程语言叫<a href="http://doc.cat-v.org/bell_labs/squeak/">Squeak</a>(老鼠间交流的语言),是一个提供鼠标和键盘事件处理的编程语言,它的管道是静态创建的。然后是改进版的<a href="http://doc.cat-v.org/bell_labs/squeak/">Newsqueak</a>语言,提供了类似C语言语句和表达式的语法和类似[Pascal][Pascal]语言的推导语法。Newsqueak是一个带垃圾回收的纯函数式语言,它再次针对键盘、鼠标和窗口事件管理。但是在Newsqueak语言中管道是动态创建的,属于第一类值,可以保存到变量中。</p>
|
||||
<p>在Plan9操作系统中,这些优秀的想法被吸收到了一个叫[Alef][Alef]的编程语言中。Alef试图将Newsqueak语言改造为系统编程语言,但是因为缺少垃圾回收机制而导致并发编程很痛苦。(译注:在Alef之后还有一个叫[Limbo][Limbo]的编程语言,Go语言从其中借鉴了很多特性。 具体请参考Pike的讲稿:http://talks.golang.org/2012/concurrency.slide#9 )</p>
|
||||
<p>Go语言的其他的一些特性零散地来自于其他一些编程语言;比如iota语法是从[APL][APL]语言借鉴,词法作用域与嵌套函数来自于[Scheme][Scheme]语言(和其他很多语言)。当然,我们也可以从Go中发现很多创新的设计。比如Go语言的切片为动态数组提供了有效的随机存取的性能,这可能会让人联想到链表的底层的共享机制。还有Go语言新发明的defer语句。</p>
|
||||
<p>Go语言有时候被描述为“类C语言”,或者是“21世纪的C语言”。Go从C语言继承了相似的表达式语法、控制流结构、基础数据类型、调用参数传值、指针等很多思想,还有C语言一直所看中的编译后机器码的运行效率以及和现有操作系统的无缝适配。</p>
|
||||
<p>但是在Go语言的家族树中还有其它的祖先。其中一个有影响力的分支来自<a href="https://en.wikipedia.org/wiki/Niklaus_Wirth">Niklaus Wirth</a>所设计的<code>Pascal</code>语言。然后<code>Modula-2</code>语言激发了包的概念。然后<code>Oberon</code>语言摒弃了模块接口文件和模块实现文件之间的区别。第二代的<code>Oberon-2</code>语言直接影响了包的导入和声明的语法,还有<code>Oberon</code>语言的面向对象特性所提供的方法的声明语法等。</p>
|
||||
<p>Go语言的另一支祖先,带来了Go语言区别其他语言的重要特性,灵感来自于贝尔实验室的<a href="https://en.wikipedia.org/wiki/Tony_Hoare">Tony Hoare</a>于1978年发表的鲜为外界所知的关于并发研究的基础文献 <em>顺序通信进程</em> ( <em>communicating sequential processes</em> ,缩写为<code>CSP</code>。在<code>CSP</code>中,程序是一组中间没有共享状态的平行运行的处理过程,它们之间使用管道进行通信和控制同步。不过<a href="https://en.wikipedia.org/wiki/Tony_Hoare">Tony Hoare</a>的<code>CSP</code>只是一个用于描述并发性基本概念的描述语言,并不是一个可以编写可执行程序的通用编程语言。</p>
|
||||
<p>接下来,Rob Pike和其他人开始不断尝试将<a href="https://en.wikipedia.org/wiki/Communicating_sequential_processes">CSP</a>引入实际的编程语言中。他们第一次尝试引入<a href="https://en.wikipedia.org/wiki/Communicating_sequential_processes">CSP</a>特性的编程语言叫<a href="http://doc.cat-v.org/bell_labs/squeak/">Squeak</a>(老鼠间交流的语言),是一个提供鼠标和键盘事件处理的编程语言,它的管道是静态创建的。然后是改进版的<a href="http://doc.cat-v.org/bell_labs/squeak/">Newsqueak</a>语言,提供了类似<code>C</code>语言语句和表达式的语法和类似<code>Pascal</code>语言的推导语法。<code>Newsqueak</code>是一个带垃圾回收的纯函数式语言,它再次针对键盘、鼠标和窗口事件管理。但是在<code>Newsqueak</code>语言中管道是动态创建的,属于第一类值,可以保存到变量中。</p>
|
||||
<p>在<code>Plan9</code>操作系统中,这些优秀的想法被吸收到了一个叫<code>Alef</code>的编程语言中。<code>Alef</code>试图将<code>Newsqueak</code>语言改造为系统编程语言,但是因为缺少垃圾回收机制而导致并发编程很痛苦。(译注:在<code>Alef</code>之后还有一个叫<code>Limbo</code>的编程语言,Go语言从其中借鉴了很多特性。 具体请参考Pike的讲稿:http://talks.golang.org/2012/concurrency.slide#9 )</p>
|
||||
<p>Go语言的其他的一些特性零散地来自于其他一些编程语言;比如<code>iota</code>语法是从<code>APL</code>语言借鉴,词法作用域与嵌套函数来自于<code>Scheme</code>语言(和其他很多语言)。当然,我们也可以从Go中发现很多创新的设计。比如Go语言的切片为动态数组提供了有效的随机存取的性能,这可能会让人联想到链表的底层的共享机制。还有Go语言新发明的<code>defer</code>语句。</p>
|
||||
<h2 id="go语言项目"><a class="header" href="#go语言项目">Go语言项目</a></h2>
|
||||
<p>所有的编程语言都反映了语言设计者对编程哲学的反思,通常包括之前的语言所暴露的一些不足地方的改进。Go项目是在Google公司维护超级复杂的几个软件系统遇到的一些问题的反思(但是这类问题绝不是Google公司所特有的)。</p>
|
||||
<p>正如<a href="http://genius.cat-v.org/rob-pike/">Rob Pike</a>所说,“软件的复杂性是乘法级相关的”,通过增加一个部分的复杂性来修复问题通常将慢慢地增加其他部分的复杂性。通过增加功能、选项和配置是修复问题的最快的途径,但是这很容易让人忘记简洁的内涵,即从长远来看,简洁依然是好软件的关键因素。</p>
|
||||
<p>简洁的设计需要在工作开始的时候舍弃不必要的想法,并且在软件的生命周期内严格区别好的改变和坏的改变。通过足够的努力,一个好的改变可以在不破坏原有完整概念的前提下保持自适应,正如<a href="http://www.cs.unc.edu/%7Ebrooks/">Fred Brooks</a>所说的“概念完整性”;而一个坏的改变则不能达到这个效果,它们仅仅是通过肤浅的和简单的妥协来破坏原有设计的一致性。只有通过简洁的设计,才能让一个系统保持稳定、安全和持续的进化。</p>
|
||||
<p>Go项目包括编程语言本身,附带了相关的工具和标准库,最后但并非代表不重要的是,关于简洁编程哲学的宣言。就事后诸葛的角度来看,Go语言的这些地方都做的还不错:拥有自动垃圾回收、一个包系统、函数作为一等公民、词法作用域、系统调用接口、只读的UTF8字符串等。但是Go语言本身只有很少的特性,也不太可能添加太多的特性。例如,它没有隐式的数值转换,没有构造函数和析构函数,没有运算符重载,没有默认参数,也没有继承,没有泛型,没有异常,没有宏,没有函数修饰,更没有线程局部存储。但是,语言本身是成熟和稳定的,而且承诺保证向后兼容:用之前的Go语言编写程序可以用新版本的Go语言编译器和标准库直接构建而不需要修改代码。</p>
|
||||
<p>Go语言有足够的类型系统以避免动态语言中那些粗心的类型错误,但是,Go语言的类型系统相比传统的强类型语言又要简洁很多。虽然,有时候这会导致一个“无类型”的抽象类型概念,但是Go语言程序员并不需要像C++或Haskell程序员那样纠结于具体类型的安全属性。在实践中,Go语言简洁的类型系统给程序员带来了更多的安全性和更好的运行时性能。</p>
|
||||
<p>Go语言鼓励当代计算机系统设计的原则,特别是局部的重要性。它的内置数据类型和大多数的准库数据结构都经过精心设计而避免显式的初始化或隐式的构造函数,因为很少的内存分配和内存初始化代码被隐藏在库代码中了。Go语言的聚合类型(结构体和数组)可以直接操作它们的元素,只需要更少的存储空间、更少的内存写操作,而且指针操作比其他间接操作的语言也更有效率。由于现代计算机是一个并行的机器,Go语言提供了基于CSP的并发特性支持。Go语言的动态栈使得轻量级线程goroutine的初始栈可以很小,因此,创建一个goroutine的代价很小,创建百万级的goroutine完全是可行的。</p>
|
||||
<p>Go语言有足够的类型系统以避免动态语言中那些粗心的类型错误,但是,Go语言的类型系统相比传统的强类型语言又要简洁很多。虽然,有时候这会导致一个“无类型”的抽象类型概念,但是Go语言程序员并不需要像<code>C++</code>或<code>Haskell</code>程序员那样纠结于具体类型的安全属性。在实践中,Go语言简洁的类型系统给程序员带来了更多的安全性和更好的运行时性能。</p>
|
||||
<p>Go语言鼓励当代计算机系统设计的原则,特别是局部的重要性。它的内置数据类型和大多数的准库数据结构都经过精心设计而避免显式的初始化或隐式的构造函数,因为很少的内存分配和内存初始化代码被隐藏在库代码中了。Go语言的聚合类型(结构体和数组)可以直接操作它们的元素,只需要更少的存储空间、更少的内存写操作,而且指针操作比其他间接操作的语言也更有效率。由于现代计算机是一个并行的机器,Go语言提供了基于<code>CSP</code>的并发特性支持。Go语言的动态栈使得轻量级线程<code>goroutine</code>的初始栈可以很小,因此,创建一个<code>goroutine</code>的代价很小,创建百万级的<code>goroutine</code>完全是可行的。</p>
|
||||
<p>Go语言的标准库(通常被称为语言自带的电池),提供了清晰的构建模块和公共接口,包含I/O操作、文本处理、图像、密码学、网络和分布式应用程序等,并支持许多标准化的文件格式和编解码协议。库和工具使用了大量的约定来减少额外的配置和解释,从而最终简化程序的逻辑,而且,每个Go程序结构都是如此的相似,因此,Go程序也很容易学习。使用Go语言自带工具构建Go语言项目只需要使用文件名和标识符名称,一个偶尔的特殊注释来确定所有的库、可执行文件、测试、基准测试、例子、以及特定于平台的变量、项目的文档等;Go语言源代码本身就包含了构建规范。</p>
|
||||
<h2 id="本书的组织"><a class="header" href="#本书的组织">本书的组织</a></h2>
|
||||
<p>我们假设你已经有一种或多种其他编程语言的使用经历,不管是类似C、C++或Java的编译型语言,还是类似Python、Ruby、JavaScript的脚本语言,因此我们不会像对完全的编程语言初学者那样解释所有的细节。因为,Go语言的变量、常量、表达式、控制流和函数等基本语法也是类似的。</p>
|
||||
|
22
print.html
22
print.html
@ -164,6 +164,7 @@
|
||||
<p><img src="cover.jpg" alt="" /></p>
|
||||
<ul>
|
||||
<li>在线阅读:<a href="https://gopl-zh.github.io">https://gopl-zh.github.io</a></li>
|
||||
<li>在线阅读:<a href="https://golang-china.github.io/gopl-zh">https://golang-china.github.io/gopl-zh</a></li>
|
||||
<li>项目主页:<a href="https://github.com/gopl-zh">https://github.com/gopl-zh</a></li>
|
||||
<li>项目主页(旧):<a href="http://github.com/golang-china/gopl-zh">http://github.com/golang-china/gopl-zh</a></li>
|
||||
<li>原版官网:<a href="http://gopl.io">http://gopl.io</a></li>
|
||||
@ -175,24 +176,29 @@
|
||||
<li>译者:CrazySssst, <a href="https://github.com/CrazySssst">https://github.com/CrazySssst</a></li>
|
||||
<li>译者:foreversmart, <a href="https://github.com/foreversmart">https://github.com/foreversmart</a> <a href="mailto:njutree@gmail.com">njutree@gmail.com</a></li>
|
||||
</ul>
|
||||
<p>Go 语言中国:</p>
|
||||
<ul>
|
||||
<li>Go 语言中国:<a href="https://github.com/golang-china">https://github.com/golang-china</a></li>
|
||||
<li>Go 语言中国论坛:<a href="https://github.com/golang-china/main.go/discussions">https://github.com/golang-china/main.go/discussions</a></li>
|
||||
</ul>
|
||||
<div style="break-before: page; page-break-before: always;"></div><h1 id="前言"><a class="header" href="#前言">前言</a></h1>
|
||||
<h2 id="go语言起源"><a class="header" href="#go语言起源">Go语言起源</a></h2>
|
||||
<p>编程语言的演化跟生物物种的演化类似,一个成功的编程语言的后代一般都会继承它们祖先的优点;当然有时多种语言杂合也可能会产生令人惊讶的特性;还有一些激进的新特性可能并没有先例。通过观察这些影响,我们可以学到为什么一门语言是这样子的,它已经适应了怎样的环境。</p>
|
||||
<p>下图展示了有哪些早期的编程语言对Go语言的设计产生了重要影响。</p>
|
||||
<p><img src="../images/ch0-01.png" alt="" /></p>
|
||||
<p>Go语言有时候被描述为“C类似语言”,或者是“21世纪的C语言”。Go从C语言继承了相似的表达式语法、控制流结构、基础数据类型、调用参数传值、指针等很多思想,还有C语言一直所看中的编译后机器码的运行效率以及和现有操作系统的无缝适配。</p>
|
||||
<p>但是在Go语言的家族树中还有其它的祖先。其中一个有影响力的分支来自<a href="https://en.wikipedia.org/wiki/Niklaus_Wirth">Niklaus Wirth</a>所设计的[Pascal][Pascal]语言。然后[Modula-2][Modula-2]语言激发了包的概念。然后[Oberon][Oberon]语言摒弃了模块接口文件和模块实现文件之间的区别。第二代的[Oberon-2][Oberon-2]语言直接影响了包的导入和声明的语法,还有[Oberon][Oberon]语言的面向对象特性所提供的方法的声明语法等。</p>
|
||||
<p>Go语言的另一支祖先,带来了Go语言区别其他语言的重要特性,灵感来自于贝尔实验室的<a href="https://en.wikipedia.org/wiki/Tony_Hoare">Tony Hoare</a>于1978年发表的鲜为外界所知的关于并发研究的基础文献 <em>顺序通信进程</em> ( <em>[communicating sequential processes][CSP]</em> ,缩写为[CSP][CSP]。在[CSP][CSP]中,程序是一组中间没有共享状态的平行运行的处理过程,它们之间使用管道进行通信和控制同步。不过<a href="https://en.wikipedia.org/wiki/Tony_Hoare">Tony Hoare</a>的[CSP][CSP]只是一个用于描述并发性基本概念的描述语言,并不是一个可以编写可执行程序的通用编程语言。</p>
|
||||
<p>接下来,Rob Pike和其他人开始不断尝试将<a href="https://en.wikipedia.org/wiki/Communicating_sequential_processes">CSP</a>引入实际的编程语言中。他们第一次尝试引入<a href="https://en.wikipedia.org/wiki/Communicating_sequential_processes">CSP</a>特性的编程语言叫<a href="http://doc.cat-v.org/bell_labs/squeak/">Squeak</a>(老鼠间交流的语言),是一个提供鼠标和键盘事件处理的编程语言,它的管道是静态创建的。然后是改进版的<a href="http://doc.cat-v.org/bell_labs/squeak/">Newsqueak</a>语言,提供了类似C语言语句和表达式的语法和类似[Pascal][Pascal]语言的推导语法。Newsqueak是一个带垃圾回收的纯函数式语言,它再次针对键盘、鼠标和窗口事件管理。但是在Newsqueak语言中管道是动态创建的,属于第一类值,可以保存到变量中。</p>
|
||||
<p>在Plan9操作系统中,这些优秀的想法被吸收到了一个叫[Alef][Alef]的编程语言中。Alef试图将Newsqueak语言改造为系统编程语言,但是因为缺少垃圾回收机制而导致并发编程很痛苦。(译注:在Alef之后还有一个叫[Limbo][Limbo]的编程语言,Go语言从其中借鉴了很多特性。 具体请参考Pike的讲稿:http://talks.golang.org/2012/concurrency.slide#9 )</p>
|
||||
<p>Go语言的其他的一些特性零散地来自于其他一些编程语言;比如iota语法是从[APL][APL]语言借鉴,词法作用域与嵌套函数来自于[Scheme][Scheme]语言(和其他很多语言)。当然,我们也可以从Go中发现很多创新的设计。比如Go语言的切片为动态数组提供了有效的随机存取的性能,这可能会让人联想到链表的底层的共享机制。还有Go语言新发明的defer语句。</p>
|
||||
<p>Go语言有时候被描述为“类C语言”,或者是“21世纪的C语言”。Go从C语言继承了相似的表达式语法、控制流结构、基础数据类型、调用参数传值、指针等很多思想,还有C语言一直所看中的编译后机器码的运行效率以及和现有操作系统的无缝适配。</p>
|
||||
<p>但是在Go语言的家族树中还有其它的祖先。其中一个有影响力的分支来自<a href="https://en.wikipedia.org/wiki/Niklaus_Wirth">Niklaus Wirth</a>所设计的<code>Pascal</code>语言。然后<code>Modula-2</code>语言激发了包的概念。然后<code>Oberon</code>语言摒弃了模块接口文件和模块实现文件之间的区别。第二代的<code>Oberon-2</code>语言直接影响了包的导入和声明的语法,还有<code>Oberon</code>语言的面向对象特性所提供的方法的声明语法等。</p>
|
||||
<p>Go语言的另一支祖先,带来了Go语言区别其他语言的重要特性,灵感来自于贝尔实验室的<a href="https://en.wikipedia.org/wiki/Tony_Hoare">Tony Hoare</a>于1978年发表的鲜为外界所知的关于并发研究的基础文献 <em>顺序通信进程</em> ( <em>communicating sequential processes</em> ,缩写为<code>CSP</code>。在<code>CSP</code>中,程序是一组中间没有共享状态的平行运行的处理过程,它们之间使用管道进行通信和控制同步。不过<a href="https://en.wikipedia.org/wiki/Tony_Hoare">Tony Hoare</a>的<code>CSP</code>只是一个用于描述并发性基本概念的描述语言,并不是一个可以编写可执行程序的通用编程语言。</p>
|
||||
<p>接下来,Rob Pike和其他人开始不断尝试将<a href="https://en.wikipedia.org/wiki/Communicating_sequential_processes">CSP</a>引入实际的编程语言中。他们第一次尝试引入<a href="https://en.wikipedia.org/wiki/Communicating_sequential_processes">CSP</a>特性的编程语言叫<a href="http://doc.cat-v.org/bell_labs/squeak/">Squeak</a>(老鼠间交流的语言),是一个提供鼠标和键盘事件处理的编程语言,它的管道是静态创建的。然后是改进版的<a href="http://doc.cat-v.org/bell_labs/squeak/">Newsqueak</a>语言,提供了类似<code>C</code>语言语句和表达式的语法和类似<code>Pascal</code>语言的推导语法。<code>Newsqueak</code>是一个带垃圾回收的纯函数式语言,它再次针对键盘、鼠标和窗口事件管理。但是在<code>Newsqueak</code>语言中管道是动态创建的,属于第一类值,可以保存到变量中。</p>
|
||||
<p>在<code>Plan9</code>操作系统中,这些优秀的想法被吸收到了一个叫<code>Alef</code>的编程语言中。<code>Alef</code>试图将<code>Newsqueak</code>语言改造为系统编程语言,但是因为缺少垃圾回收机制而导致并发编程很痛苦。(译注:在<code>Alef</code>之后还有一个叫<code>Limbo</code>的编程语言,Go语言从其中借鉴了很多特性。 具体请参考Pike的讲稿:http://talks.golang.org/2012/concurrency.slide#9 )</p>
|
||||
<p>Go语言的其他的一些特性零散地来自于其他一些编程语言;比如<code>iota</code>语法是从<code>APL</code>语言借鉴,词法作用域与嵌套函数来自于<code>Scheme</code>语言(和其他很多语言)。当然,我们也可以从Go中发现很多创新的设计。比如Go语言的切片为动态数组提供了有效的随机存取的性能,这可能会让人联想到链表的底层的共享机制。还有Go语言新发明的<code>defer</code>语句。</p>
|
||||
<h2 id="go语言项目"><a class="header" href="#go语言项目">Go语言项目</a></h2>
|
||||
<p>所有的编程语言都反映了语言设计者对编程哲学的反思,通常包括之前的语言所暴露的一些不足地方的改进。Go项目是在Google公司维护超级复杂的几个软件系统遇到的一些问题的反思(但是这类问题绝不是Google公司所特有的)。</p>
|
||||
<p>正如<a href="http://genius.cat-v.org/rob-pike/">Rob Pike</a>所说,“软件的复杂性是乘法级相关的”,通过增加一个部分的复杂性来修复问题通常将慢慢地增加其他部分的复杂性。通过增加功能、选项和配置是修复问题的最快的途径,但是这很容易让人忘记简洁的内涵,即从长远来看,简洁依然是好软件的关键因素。</p>
|
||||
<p>简洁的设计需要在工作开始的时候舍弃不必要的想法,并且在软件的生命周期内严格区别好的改变和坏的改变。通过足够的努力,一个好的改变可以在不破坏原有完整概念的前提下保持自适应,正如<a href="http://www.cs.unc.edu/%7Ebrooks/">Fred Brooks</a>所说的“概念完整性”;而一个坏的改变则不能达到这个效果,它们仅仅是通过肤浅的和简单的妥协来破坏原有设计的一致性。只有通过简洁的设计,才能让一个系统保持稳定、安全和持续的进化。</p>
|
||||
<p>Go项目包括编程语言本身,附带了相关的工具和标准库,最后但并非代表不重要的是,关于简洁编程哲学的宣言。就事后诸葛的角度来看,Go语言的这些地方都做的还不错:拥有自动垃圾回收、一个包系统、函数作为一等公民、词法作用域、系统调用接口、只读的UTF8字符串等。但是Go语言本身只有很少的特性,也不太可能添加太多的特性。例如,它没有隐式的数值转换,没有构造函数和析构函数,没有运算符重载,没有默认参数,也没有继承,没有泛型,没有异常,没有宏,没有函数修饰,更没有线程局部存储。但是,语言本身是成熟和稳定的,而且承诺保证向后兼容:用之前的Go语言编写程序可以用新版本的Go语言编译器和标准库直接构建而不需要修改代码。</p>
|
||||
<p>Go语言有足够的类型系统以避免动态语言中那些粗心的类型错误,但是,Go语言的类型系统相比传统的强类型语言又要简洁很多。虽然,有时候这会导致一个“无类型”的抽象类型概念,但是Go语言程序员并不需要像C++或Haskell程序员那样纠结于具体类型的安全属性。在实践中,Go语言简洁的类型系统给程序员带来了更多的安全性和更好的运行时性能。</p>
|
||||
<p>Go语言鼓励当代计算机系统设计的原则,特别是局部的重要性。它的内置数据类型和大多数的准库数据结构都经过精心设计而避免显式的初始化或隐式的构造函数,因为很少的内存分配和内存初始化代码被隐藏在库代码中了。Go语言的聚合类型(结构体和数组)可以直接操作它们的元素,只需要更少的存储空间、更少的内存写操作,而且指针操作比其他间接操作的语言也更有效率。由于现代计算机是一个并行的机器,Go语言提供了基于CSP的并发特性支持。Go语言的动态栈使得轻量级线程goroutine的初始栈可以很小,因此,创建一个goroutine的代价很小,创建百万级的goroutine完全是可行的。</p>
|
||||
<p>Go语言有足够的类型系统以避免动态语言中那些粗心的类型错误,但是,Go语言的类型系统相比传统的强类型语言又要简洁很多。虽然,有时候这会导致一个“无类型”的抽象类型概念,但是Go语言程序员并不需要像<code>C++</code>或<code>Haskell</code>程序员那样纠结于具体类型的安全属性。在实践中,Go语言简洁的类型系统给程序员带来了更多的安全性和更好的运行时性能。</p>
|
||||
<p>Go语言鼓励当代计算机系统设计的原则,特别是局部的重要性。它的内置数据类型和大多数的准库数据结构都经过精心设计而避免显式的初始化或隐式的构造函数,因为很少的内存分配和内存初始化代码被隐藏在库代码中了。Go语言的聚合类型(结构体和数组)可以直接操作它们的元素,只需要更少的存储空间、更少的内存写操作,而且指针操作比其他间接操作的语言也更有效率。由于现代计算机是一个并行的机器,Go语言提供了基于<code>CSP</code>的并发特性支持。Go语言的动态栈使得轻量级线程<code>goroutine</code>的初始栈可以很小,因此,创建一个<code>goroutine</code>的代价很小,创建百万级的<code>goroutine</code>完全是可行的。</p>
|
||||
<p>Go语言的标准库(通常被称为语言自带的电池),提供了清晰的构建模块和公共接口,包含I/O操作、文本处理、图像、密码学、网络和分布式应用程序等,并支持许多标准化的文件格式和编解码协议。库和工具使用了大量的约定来减少额外的配置和解释,从而最终简化程序的逻辑,而且,每个Go程序结构都是如此的相似,因此,Go程序也很容易学习。使用Go语言自带工具构建Go语言项目只需要使用文件名和标识符名称,一个偶尔的特殊注释来确定所有的库、可执行文件、测试、基准测试、例子、以及特定于平台的变量、项目的文档等;Go语言源代码本身就包含了构建规范。</p>
|
||||
<h2 id="本书的组织"><a class="header" href="#本书的组织">本书的组织</a></h2>
|
||||
<p>我们假设你已经有一种或多种其他编程语言的使用经历,不管是类似C、C++或Java的编译型语言,还是类似Python、Ruby、JavaScript的脚本语言,因此我们不会像对完全的编程语言初学者那样解释所有的细节。因为,Go语言的变量、常量、表达式、控制流和函数等基本语法也是类似的。</p>
|
||||
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
Loading…
Reference in New Issue
Block a user