是什么让我大二从 Java 转向 C++?
大家好,我是小北。
之前写了一篇关于如何系统学习 C++的文章,然后就有小伙伴留言让我写写该如何学习 C 语言。
本来今天是更新指针、内存模型的这块东西的,但是想了下,还是先把如何学好 C 语言出了,毕竟内存模型这些具体的技术,大家都能找到很多博客的。
而我想站在自己的角度,写写作为一个遇到 Java 就放弃了 C 的渣男,最后又是如何爱上 C 并且把它学好的。
但是呢,还是分为两篇,第一篇是关于我为什么如此推荐大家学习 C 语言。
熟悉我的读者都知道,我之前多次在文章中提到 C 语言是基础,不管做什么方向,只要你吃编程这碗饭,我都建议系统学一下。
这是为什么呢?
在这里引用一段不知出处的话作为回答:
CPU 体系结构、汇编、C语言(包括C++)和 操作系统,永远都是编程大师们的护身法宝,就如同少林寺的《易筋经》,是最为上乘的武功;学会了《易筋经》,你将无所不能,任你创造武功;学会编程“易筋经”,大师们可以任意开发操作系统、编译器,甚至是开发一种新的程序设计语言!
-- 佚名
这段话读下来,我觉得有必要先弄个狗头保命🤣,不然可能会被其它语言爱好者喷了。
首先,这段话不是我写的,其次,里面很多表述也有点不敢苟同,比如:“你将无所不能”、“最为上乘”......
我从不认为语言和各种技术有优劣之分,也不是任何语言的狂热爱好者。
这些语言就是木工的不同工具而已,不能说有了锉刀,就不要斧子了。
但是我十分认可这段话所传达的系统、体系结构等底层知识的重要性。
读大学的时候,我大概经历了从学习 C -> 学不会 -> 讨厌 C -> 喜欢 Java,做 Web 开发 -> 然后回归到学习汇编、C 语言操作系统 -> 尝试着跟着教程“抄”一个 mini os。
大一 C 语言学了个寂寞,最重要的指针基本上是似懂非懂,动态内存也是云里雾里。
导致我真的很难用 C 写一点像样的程序,经常遇到各种内存错误,再加上简陋的标准库,这让我也从心里抗拒 C 语言。
所以后来接触 Java 后,感觉发现了新大陆,String 的操作原来可以这么简单。
也不会再有各种恶心的内存错误,顶多偶尔来个 NullpointerException。
但是 Java 学到后面,我发现我还是离不开 C 和 操作系统。
比如当时学 NIO、Selectors 的时候,了解到了多路复用这种技术,饶了一圈最终还是得回归到操作系统提供的系统调用,poll、epoll、select 这些上去。
并且有时候追 JDK 源码的时候,追到最后经常看到各种 Native 方法的调用,还是 C/C++。
所以这就给我一种感觉,要想真正掌握 Java 封装的这些类库原理,还是离不开底层这些技术,而 C/C++ 则是学习这些技术最好的窗口。
并且那时候经常会想一些这样的一些问题:
malloc 分配的内存是从哪来的呢?(brk、操作系统内存管理等) hello.c 编译完了长什么样子呢?(PE/ELF 文件格式) 目标文件到底是啥,怎么链接在一起的? 为啥 Java 不需要链接?(实际上也是需要的,只不过是运行时类动态加载) 程序在内存中到底是怎么存在的?(加载、内存布局) ......
所以后来我就下定决定要把 C/C++ 从头再学一遍,然后开始学习一些底层技术。
这也回答了今晚一个读者问我的问题:
当然了,我现在工作没有从事以前喜欢的 infra 开发,更多的写业务,但是我也在持续学习着做 infra 开发所需要的一些技能。
PHP、.Net、Java 这些语言封装得很好,开发效率确实很高,但是对于程序员来说可能不太好,主要是两个方面:
丰富的类库屏蔽了大量的细节。
JVM 等虚拟机也屏蔽了操作系统的系统调用和底层机制。
现在很多程序员都在说技术焦虑,新出的框架太多,学习的速度永远赶不上新技术的发展。
那缓解这种焦虑的方法就是你掌握一些领域的核心基础知识和底层的技术。
因为近十几年,计算机基础理论方面几乎没有任何突破性发展,大学学的那些基础课程也是十几年未变,图形学、操作系统、编译原理虽然不断有新技术、论文发表,但核心的始终没变。
掌握这些基础知识,把我们个人工作所从事的领域技术栈自下而上打通,这也是我目前想做的一件事。
今年的话就先从公司的 RPC 框架原理、部分源码入手,再研究下 Protobuf 这些源码。
做这些一是为了提高技术,而是为了更好的工作,了解原理和实现,线上出问题了才能第一时间找到定位问题的方向,不至于灯下黑。
时间再充足一些的话,再去看下开源的一些服务端框架设计思想,比如搜狗 Workflow、brpc 等。
围绕着工作点亮周边技术栈也是一个不错的选择。
比如,你是做 Web 开发的,业余就去深入研究下各种 Web 框架的实现原理、架构、协议、序列化、Web安全、服务器、分布式问题以及各种中间件等。
掌握这些技术最好和底层知识打通,比如你用 SQL 往数据库里写了条数据。
那应该清楚的知道这条 SQL 是如何被解释执行的,用到了哪些索引,数据库是如何去访问、过滤这些数据的,然后又是怎么传输到客户端的?
数据库又是如何组织磁盘的?数据在磁盘上是如何组织的?
这些过程都搞透彻了,线上出问题了才知道该从哪里排查,可能是中间哪一步出的问题。
这些知识平时似乎不掌握也没事,只要会 SQL 就行了,但是关键时候却能发挥大作用。
那么如何建立这样的知识体系呢?
这让我想起曾经在知乎上看到的一个回答:
答主就是从数据库这个领域下手,花了几年时间刻苦专研,做到了这方面的专家。
在公司部门内逐步建立起技术影响力,还帮助其它部门做性能优化,系统设计等。
当然,这样深入的知识体系除了给他带来技术上成长以外,薪资和职级上也自然是颇为丰厚。
好了,杂七杂八的写了些没什么逻辑的文字,最后来收下尾吧。
这篇文章主要就是想告诉还在学校或者跟我一样才毕业不久的同学,重视基础和技术深度。
说白了就是你得了解底层系统的机制,知其然也要知其所以然。
而 C 语言和操作系统是学习底层系统机制的最好方式,只此一家。
争取做到基础深厚,涉猎广泛,这样才能在技术上融会贯通。
那些技术大佬都是有很强的系统知识的,表面的东西永远都是肤浅的。
好啦,今天的分享就到这里了,顺便给大家推荐一本书:
《Designing Data-Intensive Application》
简称,DDIA,也是被很多大 V 推荐过的一本书。
这本书以数据为核心,从抽象层次上详细论述了各种数据存储模型,包括传统关系型数据库、NoSQL、大数据存储、流式数据存储等等,由浅入深。
虽然这些方面平时或多或少都接触过一些,但是说实话很多内部机制、各种数据存储的利弊、如何取舍都理解得非常粗浅,这本书读下来有一种让人豁然开朗的感受。
正所谓数据是架构的核心,推荐所有后台开发工程师都去读一下,其实现在的互联网业务,本质上就是一个数据处理系统:一个浅应用层包裹着的复杂的数据系统,充分理解数据系统的运作和设计非常必要。
我仿佛记得以前推荐过?
有读者还来感谢过我推荐这本书。
但是好书多推荐几次也无妨。
现在晚上有时间就会看上几页:
哈哈哈突然想起,这里可以放一个链接,大家想买书的可以从我这里购买,我好像有几块提成?
— 【 THE END 】— 本公众号全部博文已整理成一个目录,请在公众号里回复「m」获取! 3T技术资源大放送!包括但不限于:Java、C/C++,Linux,Python,大数据,人工智能等等。在公众号内回复「1024」,即可免费获取!!