当前位置: 首页 > 科技观察

90后“老人”与00后围棋小子的硬盘夜谈

时间:2023-03-11 21:32:08 科技观察

1.初次见面虽然这个目录下各种编程语言写的程序层出不穷,但Java还是怀念不幸去世的老C。他经常跟同目录的Python和Ruby说C老头知识渊博,贴近硬件运行,速度很快,能从他身上学到很多东西等等。今天有一个新人进入了目录。Java只看文件名“hello.go”就知道这是一门新语言。这种语言叫Go吗?使用动词作为语言名称是相当罕见的!java赶紧上网一搜,我说,这家伙2009年出生的,快10岁了,太年轻了。我们这些90后真的变老了!一群90后的老家伙,Java、Python、Ruby……围着00后的围棋程序,仔细打量着他们:“新来的,有什么本事?”戈有些害怕:“你要干什么?”好吧,KenThompson,RobPike是我自己的父亲,小心点!”Python悄悄问Java:“这两个人到底是什么东西?”:“KenThompson是Unix和C的创始人,RobPike是Unix和C的设计者UTF-8!这还不是主要的,关键是谷歌给这小子背书了。”下来。“按照惯例,新人要来个HelloWorld,交个名证吧!”“又来一个把类型放在变量名后面!”Java看到这种语法就怒了!“Mr.Java,你们JVM平台上的Scala和Kotlin不都是这样吗?”2000后的围棋小伙见多识广,用自己的方式来对抗对方。“那两个小子敢来,我一定会的打败他们。你的语法老是让我觉得很生气!”Java竟然自称是个老头子,真的老了。“好吧,让我们冷静一下。我老了,真气逆行。发疯了可不好!”Python安慰道。“不过这小子的变量是要有类型的,而且好像是静态类型的语言,而且他是我们这一代人。”Java心里稍稍舒了口气。“你们这辈谁啊?仔细看看这个变量声明,完全没有指定类型,声明后面也没有分号,跟我们Python是一家。”Python开始向Go靠拢。Java“老头”不屑的说道:“这个小把戏你还不懂?这就是自动类型推断,我们的Kotlin已经玩烂很久了!就说名字吧,已经声明为字符串类型了,它不能如果你再改变它,尝试将它分配给一个整数?我敢打赌编译器会报错!2.审问由于静态类型的盟友,Java对Go有了一点好感。就一门语言而言,必须有几种基本的数据结构,比如数组、列表、HashMap。你应该把它们都内置了,对吧?”“那很自然。现在已经不是C语言的时代了。常用的数据类型都得内置,没有它们怎么能乱来!”Go立马回道。“流控语句大概也差不多,不想看你是如何实现用户自定义类的?”自称是本目录老大的Java代表大家继续发问。Go说:“很简单。我们跟C老头学了一个struct。”听到C老头,Java眼睛一亮,语法真的和C差不多。“咦?这只是属性数据,没有相关的方法吗?”Python不让Java独霸,急忙问道。“很简单,写一个方法就行了!”“方法和属性分开不在一起,好奇怪!大家都喊道:“我们都有public、private这样的权限限定符,你怎么处理的?”Ruby问道。“这里很简单,如果一个标识符(如方法、变量等)以大写字母开头,就表示它是public的,可以访问其他包的代码,否则就是private的!”众人惊呼,这。..这想象力有点太丰富了吧!“你如何处理继承问题?”“我这里其实没有继承,我这里只有组合:”又是一阵惊呼,大家将这个方法和自己的实现进行了比较。Java老哥想到了面向对象的设计。重要原则:“优先使用组合而不是继承”,我觉得Go的思路还是挺不错的。“那你能实现多态吗?”“不用说了,我实现的方式也很简单,没必要强行让一个类去实现一个接口,只要你有和接口一样的方法,就当那个接口来用!”“这不是和我们的鸭子打字一样吗!”Python和Ruby异口同声地说,“只要你长得像鸭子,走路像鸭子,不管你有没有实现duck接口,我们都会认为你是鸭子!”3.GoroutineJava不支持DuckTyping,他有点不爽,撇撇嘴说:“怎么回事,都是些小把戏。我问你,你的多线程编程怎么样??这是能否在服务端高并发的恶劣环境中生存下来,关键!”Go说:“我没有多线程!”没有线程?大家都瞪大了眼睛,那怎么支持并发呢?“但是我有goroutine,可以认为是一个轻量级的线程。”“嗯,现代语言怎么能不支持并发呢?你的goroutine有什么特点?”爪哇问道。“goroutine和线程很像,就是一段可以运行的代码,在函数调用前加上go关键字就可以启动一个goroutine,是不是很简单?”“告诉我你是如何实施的?”“当你创建一个goroutine时,它??将被添加到一个全局运行队列中,然后调度程序将它们分配给一个逻辑处理器,该处理器将绑定到goroutine实际运行的唯一操作系统线程,如果一个逻辑processor有多个goroutines运行,那么应该形成一个队列,让逻辑processor调度执行。”(可以有多个逻辑处理器)《如果一个goroutine需要读写文件,阻塞了怎么办?》Java很关心这个问题。“简单,让这个goroutine脱离逻辑处理器,直接绑定到系统线程,读写文件后,回到一个逻辑处理器的队列中。”“那么你已经实现了一个线程调度器,”Python惊呼道。“是啊,你们不就是这么玩的吗?”去反问。Java、Python、Ruby自然不这么玩。没有逻辑处理器这样的东西。和Java一样,用户空间的线程直接映射到系统的核心线程执行。“虽然goroutines是轻量级的线程,但是它们是如何通信的呢?”爪哇问道。“我的创始人发明了一个东西,叫Channel,你可以把它理解为一个通道,每个goroutine都可以通过这个通道发送和接收数据!”goroutine其实就像一个线程实现在用户空间的程序中,非常轻量级,需要的空间很小,切换也发生在用户空间,开销极小。所以非常适合创建大量的goroutines来并发执行请求。4.EXE文件“嘿,这孩子创建了一个hello.exe来运行。”露比观察得很仔细。原来的C老头也被编译成exe执行了。Ruby的这一发现一下子引起了大家的嫉妒,因为这里的90后,不管是Java,Python,Ruby,还是PHP,其实都有一个虚拟机来帮助他们执行程序,他们都想体验一下飞起来的感觉exe并直接在硬件上执行,但没有机会。Java的一个优点是Hotspot的虚拟机可以将一些热点代码转换成机器指令,在硬件CPU上执行。这让Java自夸了很多天。没想到还有一个直接生成exe执行。Java想起了之前C老头说的地狱指针和内存管理,当即抛出一张王牌:“你有自动内存管理吗?”这个目录下的大部分语言都是由虚拟机自动管理的。一问,心里升起了一些优越感。“当然!你只需要创建对象,分配内存,Go会自己做垃圾回收。我爸说,我们必须改进C语言不好用的部分!”这些让大家震惊了,一个exe程序就能自动管理内存,我们以后还有出路吗?“你看,这个exe文件好大啊。”有人喊道。如果是这样,一个小小的hello.exe居然有1M多,这是怎么回事?“我们的Go语言默认是静态链接的,exe会在运行时添加所有需要的东西,所以你可以复制exe到任何地方运行,多么方便!而且,我们的exe文件也包含垃圾收集不是吗?”Java说:“啊,我明白了,其实你的每一个exe文件都已经包含了一个类似于虚拟机的运行时,对吧?不然你怎么自动收集垃圾,进行goroutine执行呢?”调度。”大佬的优越感稍微恢复了一些,至少不会比别人差。夜深了,Java做了一个完美的总结:“新来的Go小子的代码有点Pythonic,简洁干练,骨子里却流淌着静态打字的血液。他的封装、继承、多重状态和goroutine是如此不同,但总能在某种语言中找到一点影子。虽然可以编译成EXE,性能也不错,但实际上是有运行时的。好像吸收了很多语言的特点。”众人纷纷表示同意,鸟兽便散去。