周末来个王炸!!
今天是 1024 ,祝广大的程序员朋友们,节日快乐!
本来过节,能稍微放松下,打算去图书馆学习的,但是石家庄这边 yq 又严重了。更没想到周末竟然来了个王炸!之前石家庄这边就已经有一些 yq 密接,没想到昨天 yq 反而加剧了,还有人核酸是阳性!我不夸大描述,索性列出来一些事实吧:
昨天上午的时候我去图书馆学习,管理人员要求出示健康码和行程码,这在之前从来没有过。 上午的时候有一些消息表明某某小区又被封锁了。 市五院停诊的消息上了热搜。 下午的时候又有一些小区被封锁了,并要求全员核酸。 我们旁边隔壁的小区被封锁了。 为了应对 yq,我们打算去菜市场囤点菜,结果万人空巷,还好去的早,很幸运的抢到了一些菜,过了半个小时,菜架上已经没菜了。 有朋友给我发过来某某超市货架上的泡面、速食已经空了。 公布了核酸阳性居民的行程轨迹,离我们还很近。 有某某小区已经被集体隔离了。 昨天一晚上我至少听到几十辆救护车在路上,而且都是 3 - 4 辆集体出动。 今天早上看到隔壁又一所小区被封锁了,凌晨全员核酸检测。
不得不说 zf 这次动作非常快,但凡有密接,马上切断传播源,值得点赞。
希望这次 yq 能早点过去。毕竟我只想过周末,不想放长假啊。。。。。。
为了让学习更有趣,这篇文章我会列出计算机科学理论和一些概念,并且用类比的方式和尽量少的技术术语来为你进行解释。这样做的目的就是为了让你快速了解计算机,查漏补缺。
如果对这些概念有任何解释不妥之处,请及时指正我。
虽然这些概念能够快速帮助你去理解,但是这并不是一种最好的学习方式,如果你想要完整的理解这些概念,去看相关书籍或者论文。
1. 核心概念:数据结构和算法
1.1 排序
排序大家可以看一下这个视频,这是我的视频号,大家顺手点个赞并且关注一波呀。
1.2 递归
当你坐在电影院正准备好看电影的时候,这时候刚来电影院的人问你坐的是第几排,你懒的数就问前面的人,“哥们,你那一排是第几排?”你只需要从对方口中得知他的行号 + 1 就是你坐的行号,但是你前面那哥们也做了同样的事情,他也问了他前面的人。。。。。。依此类推,一直问到第一排,他回答:“我这是第一排!” 然后从现在开始,正确的行号将会一直 + 1 直到传达给刚进电影院的那哥们。
千万别在电影院这么做,否则第二排或者第三排的人可能会被第一排的当成傻子。。。。。。因为第二排的人问第一排的人:“哥们,你坐第几排?” 想象一下这个场景。。。。。。
我给你几幅图,让你理解一下什么是递归
。
1.3 大数据
假设你有一个花园,但是你花园中的水管漏水,你需要拿一些桶和密封材料来解决这个问题,但是过了一会儿,你发现实际泄漏的要大的多,你需要水管工拿更多的工具来处理,同时,你仍在使用水桶排水。过了一会儿,你发现地下有一条巨大的地下溪流已经打开。你需要每秒处理数加仑的水。
这时候桶就没用了,你需要一种全新的方法来解决这个问题,因为水的体积和速度都在增加。为了防止城镇发生洪水,你需要 zf 建造一座大型水坝,然而这需要大量的土木工程专业知识和复杂的控制系统。
大数据描述了使用传统数据处理工具无法管理的庞大而复杂的数据集。
1.4 数据结构
关于数据结构,每位程序员都应该知道
数组 https://en.wikipedia.org/wiki/Array_data_structure 树 https://en.wikipedia.org/wiki/Tree_%28data_structure%29 栈 https://en.wikipedia.org/wiki/Stack_%28abstract_data_type%29 队列 https://en.wikipedia.org/wiki/Queue_%28abstract_data_type%29 图 https://en.wikipedia.org/wiki/Graph_%28abstract_data_type%29 哈希表 https://en.wikipedia.org/wiki/Hash_table 链表 https://en.wikipedia.org/wiki/Linked_list 堆 https://en.wikipedia.org/wiki/Heap_%28data_structure%29
2. 核心概念 AI
2.1 贪心算法
想象一下,你要去徒步旅行,而你的目标是尽可能到达最高峰,在开始之前你已经有了地图,但是地图上显示了成千上万条路,但是你无法评估每一条,所以扔掉了地图,你从一个看起来很简单的路开始走,这种方式就是根据感性来选出来的,是一种贪婪和短视的表现,你选择只走最倾斜向上的路线。
但是旅行结束后,全身酸痛,你查看地图却发现旁边有一条泥泞的小河,跨过去就好了,而不用一直向上走。
贪心算法会选择当下的最佳路线,而不是重新开始考虑评估选择。
2.2 爬山算法
这次你要爬另一座山,你决定要找到能够带你到达最高峰的那条路。但是很不幸,你的地图丢了,而且山上雾气很大,那怎么办呢?所以你为了让旅途更轻松,你下载了一个 app ,这个 app 能够跟踪你走过的路测量你当前的高度。于是你每次走过的路线都是能够把你带到最高峰的路线,但是在中途,你选择了一条另外的路线,而这个路线也能把你带到最高峰。
2.3 模拟退火
在你前面的是珠穆朗玛峰。
这是你所面临的最大的挑战。你的目标是登顶,但是一遍又一遍爬珠峰是不切实际的,所以你只有一次机会。你现在非常谨慎,你不会总是向上爬,而是偶尔移动到一个比较低的点来探索其他可能的路径,以减少出错的机会,你爬的越高,你移动到较低点进行探索的可能性就越低。
2.4 动态规划
父亲:在一张纸上写下 “1+1+1+1+1+1+1+1 =”。
父亲:那等于什么?
儿子:三秒后数了数等于 8 。
父亲:在左侧写下另一个“ + 1”。
父亲:现在等于多少?
儿子:立刻确定了是 9 !
父亲:现在为何你数的这么快?
儿子:因为你刚刚才加了一个!
父亲:所以你不需要重新数,而是记住了刚刚那个数字等于 8 !
2.5 P 和 NP 的问题
P vs NP 是计算机科学领域中最流行和最重要的未解决问题之一。
假设我给你一个乘法问题,例如:
Q1:P = 7 * 17
答案是119 。这个很容易算吧?如果我颠倒这个问题怎么办:
Q2:P * Q = 119 (P 和 Q 都不能是 1 或者 119)
如果你没有看到 Q1,你要解决 Q2 ,你可能会从 2 开始尝试,一直遍历到 118 为止。所以我们还没有一种找到一个数因数的高效算法。
如果我问你,P 可能是 7 吗?这时候你可以轻松验证答案吗?你当然可以,只需要将 119 / 7 就可以了。
乘法很容易,但是找到一个数的原始因数却很难。
所以 Q1 是一个 P(多项式) 问题,它很容易得到解决,因为计算机可以轻松的将任意两个数相乘。
但是 Q2 是一个 NP(非多项式) 问题,它很难解决,找到 119 的因数对计算机来说还是很容易解决的,但是 500 位数字呢?现在对任何计算机都是不可能的。
这是这个问题的最重要的部分:NP 问题(分解)是否也是 P(乘法),只是我们还没有发现解决 NP 问题的有效方法?还是人类太笨了?想象一下,存在比人类智能得多的机器或生命。他们看我们就像我们看蚂蚁一样。我们的智力水平对他们来说太微不足道了。解决 P vs NP 问题就像为他们解决 1 + 1!
那么为什么 P vs NP 问题很重要呢?如果我们能够证明 P=NP,则意味着所有 NP 问题都可以在合理的计算机时间内轻松解决。我们将能够治愈癌症(蛋白质折叠)、破解密码(RSA)等。这将会改变世界。
3. 核心概念:并发
前景提要:假设你正在某公司担任秘书,你所做的工作包括接打电话、安排会议、写文件等,你总是需要根据任务的优先级来停下手头的工作转而做其他的(工作),每次电话响起时,你都需要停止正在处理的工作。
3.1 并行
随着任务越积越多,你无法应对你的工作了,因为有太多的书写任务,你向老板抱怨,他愿意再雇个人来帮你分担书写任务。
并行允许有两个或者更多的任务同时运行,但是前提是你的 CPU 能够支持多处理能力,人只有一个 CPU ,所以一心不能二用。这也并不是一件坏事,有的时候单线程的工作效率反而更高,而中断(学习的时候被打断)是工作的天敌,这种开销实在是太大了。
所以你和新招的那个雇员一起分担书写任务就是一种并行
。
并发概念的引入也引发了很多很多问题,比如下面的竞态条件。
3.2 竞态条件
这里就不得不提我们大家都耳熟能详的银行转账这个例子了:
你的银行账户里有 1000 元。 有人转给你 500 元,而你从 ATM 中提取了 300 元。 假设这两笔交易同时进行,两笔交易都会看到你当前的余额是 1000 元(注意这是两笔交易,这两笔交易之前彼此不可见,这点很重要)。 现在,第一笔交易给你的账户增加了 500 元,你现在就有了 1500 元。但是,第二笔交易看到的你的账户余额还是 1000 元,他从 1000 元中扣除了 300 ,变成了 700 元。 所以你现在的账户余额会变为 700
元,而不是1200
元,因为第二笔交易覆盖了第一笔交易。发生这种情况是因为银行系统不知道其他正在进行的交易。
那么,你应该如何处理这种情况呢?下面是几种解决方式。
3.3 互斥
现在我们采用这种方式:只要有正在进行的交易,系统就会锁定交易中涉及的账户。而且系统会认定转账开始 -> 转账完成是一个完整的事务周期。
所以这一次,当第一笔交易发生的那一刻,你的账户会被锁定,你不能再从你的账户中取钱,直到第一笔交易完成为止。
所以互斥是不是就解决问题了?
虽然互斥能解决系统数据安全性的问题,但是却不符合人的感性认知。但没有人希望每次有正在进行的交易时都被 ATM 拒绝。
所以我们需要修改一下方案。
3.4 信号量
二进制信号量
现在我们需要为不同类型的交易设置不同的优先级。假如提现请求的优先级要高于银行转账的优先级。所以当你从 ATM 中取款时,这笔交易的优先级要大于向你账户转账的优先级,所以此时转账的的交易会暂停,而提现的事务优先进行,因为它具有更高的优先级,等到提现成功后,转账事务再恢复。
二进制信号量很简单,1 = 正在进行的交易, 0 = 等待。
计数信号量
计数信号量允许多个进程同时运行。
假设你是一家游泳馆的工作人员,有 10 个储物柜,每个储物柜都有一把钥匙,每次收到或者分发钥匙时,你都需要把控所有的钥匙数量,如果所有储物柜都满了,其他人必须排队。每当有人完成时,他会将钥匙交给队列中的第一个人。
3.5 死锁
死锁是另外一种并发中的共性问题。
还是让我们拿银行转账来举例子。请记住,只要有正在进行的事务,就会锁定对银行帐户的访问。
假如你向张阿姨转账 500 元(来让张阿姨高兴一下),同时张阿姨向你转账 1000 元(让你补补身子)。 于是事务 A 锁定了张阿姨的账户,并且从她的账户里扣除了 1000 元。 事务B 锁定你的账户,并且从你的账户里扣除了 500 元。 然后,事务 A 尝试访问你的账户来添加她给你转账的 1000 元。 同时,事务 B 尝试访问张阿姨的账户来添加你给她转账的 500 元。
但是,由于两项交易都没有完成,因此两个事务都无法访问锁定的帐户,造成两个事务都在等待对方事务的结束,这种情况就是死锁。
还有为什么谈恋爱的过程中男生要主动一些,如果你不主动,可能就死局(死锁)了。
4. 核心概念:计算机安全
4.1 计算机黑客
计算机黑客类似于强制闯入你的房子里,下面有几种流行的黑客技术。
暴力攻击
这种做法就是尝试使用成百上千种不同的密码。有经验的黑客会先尝试最常用的密码。
暴力攻击会尝试所有可能的密码,通常首先猜测常用的密码,如“123456”、“abcdef” 等。
我之前尝试过用 kali linux 配上专用的设备跑过包破解过邻居家的 WI-FI ,结果密码只是 000000 。
社会工程
这是一项强大的技术!!!我愿称之为网络 Pua!!!
一对夫妇刚搬进隔壁。他们真的很好,乐于助人。他们经常请你吃晚饭。有一天,你说你很快就会去度假两周。他们高兴地提出要照顾你的狗。你给他们留了一把备用钥匙。从那以后,你再也没有听到关于他们的任何消息。
社会工程学会诱骗用户透露他们的私人信息。
此处应该要有个配图。
安全漏洞
安全漏洞就是黑客入侵你家能找到的缺口,比如你可能没关窗户。
特洛伊木马
黑客冒充水管工,让你帮他开门,他修理了你漏水的水管,但是他走后,你发现你的首饰不见了。
特洛伊木马是假装有用并在后台运行恶意代码的恶意软件程序。
RootKit
你的门锁被卡住了,你打电话给锁匠。他修理了你的门锁并偷偷复制了另一把钥匙。
Rootkit 通过社会工程等多种方式获得计算机管理员或 root 访问权限,然后伪装成杀毒软件难以检测到的必要文件。
DDos
这是一个书店的比喻。
假如你有一个书店,书店里面能容纳 200 多人,某一天突然有 200 多人进入你的书店,你的书店满了,而且你不能赶走他们,因为他们看起来互相都不认识,而且他们似乎真的都有兴趣买书,甚至有人问你 xxx 书在哪里,然而柜台上只有一个人付了几块钱。
人们不断进出几个小时,但是你卖的书还不到 5 本,你觉得你这个书店还能撑多久?
DDoS 试图通过大量访问者来关闭站点或服务。
4.2 密码学
对称加密
假设老王和老刘想要互相发送东西。为了确保没有人可以看到他们的东西,他们用一个盒子锁起来。他们为锁制作了 2 个相同(对称)的钥匙,并事先见面共享钥匙。
非对称加密
在两个人之间共享密钥能够正常工作,但是如果老王想和老赵交换东西,而且还不想让老刘知道该怎么办?重新共享一个全新的钥匙吗?那假如老王想和 10 个不同的人交换东西该怎么办?难道要消灭掉解决问题的老王吗?
所以老王想出了一个绝对fashion的主意:现在老王只维护一把钥匙(私钥),她将另一把钥匙(公钥)分给他的朋友们,任何人都能够加密,但是只有她有打开(解密)的钥匙,现在,任何人都能够使用她发的公钥进行加密,而且老王不需要再为任何人管理不同的钥匙。
5. 核心概念:软件开发方法
5.1 瀑布开发方式
你需要弄清楚所有的事情并记录下来,就像是瀑布一样,除非重新开始,否则无法返回。只有当前阶段完成后,你才能进入下一阶段。
5.2 敏捷开发
这是国内大多数软件公司采用的软件开发方式 --- 敏捷开发。
一开始你就弄清楚一些你需要做的事情,然后随着开发的进行,不断改进、发展协作和适应。
就像大多数产品经理或者你的领导说的:先弄一版出来再说。
5.3 现实世界中的软件开发
现在你毕业了。你编写了你认为比较漂亮的代码,一切都很完美。现在我给你介绍一种 牛仔编码,这是大学教授没有教你的开发方法。
你可能想知道为什么你不会评估开发事件,请看下图。
总结
这篇文章我给你整理了一些计算机科学中的一些常见概念,并且用生动形象的例子来为你阐述这些概念,希望能降低你学这些内容的门槛。
还是那句话,如果你想要完整的理解这些概念,去看相关书籍或者论文。
最后,希望大家三连支持哦!你的支持就是我写作最大的动力!!!