分类 阅读笔记 下的文章

获取

https://download.dre.vanderbilt.edu/

真不容易,实际上源码就是大名鼎鼎的ACE

Douglas C. Schmidt教授的主页,这里非常感谢Doug教授

小记

最近在看 《面向模式的软件架构》——并发和联网模式,google了好久都没找到源码资源

书中说能通过 http://www.posa.uci.edu获取相关示例,但此网站也无法访问

接着又试着用邮箱联系 patterns@mchp.siemens.desiemens-patterns@cs.uiuc.edu也全部不可达

后面只能尝试找原作者索要份,用我的渣渣英语尝试联系,得亏Doug教授看的懂hh

1 面试的3种形式

  • 电话面试

    • 尽量用形象的语言说清楚细节
    • 对未听清、未听懂的问题,要积极询问面试官
  • 共享桌面远程面试

    • 思考清楚前再开始编码
    • 良好的编码风格
    • 先写单元测试,再写解决问题的函数(这种测试在前、开发在后的程序员非常的稀缺)
  • 现场面试

    • 预估好出行时间
    • 得体的穿着
    • 邀请函的面试流程
    • 准备几个问题

注:目前因为疫情原因,电话面试、远程面试的占绝大多数

2 面试的3个环节

面试的3个环节

2.1 行为面试环节

算是一个暖场环节,面试官参照简历了解应聘者;通常会让应聘者做个自我介绍,而此时的自我介绍不用花太多时间,30~60秒时间介绍自己的主要学习、工作经验

2.1.1 应聘者的项目经验

STAR模型

Situation: 比如项目规模,开发的软件功能、目标用户等

Task: 需要区分“参与”和“负责”

Action: 介绍系统框架的特点、平台应用了哪些技术、测试手段等

Result: 最好能具体且有数字加以说明;比如性能提升多少,修改了多少个BUG

面试官对项目经验最常问的问题类型:

  • *你再该项目是碰到的最大问题是什么,你是怎么解决的?
  • 从这个项目中你学会了什么?
  • 什么时候会和其它团队成员(开发、测试、项目经理等)有什么样的冲突,你们是怎么解决冲突的?

总结: 主要突出介绍自己完成的工作及取得的成绩

2.1.2 掌握的技能

和描述项目时要注意“参与”和“负责”一样,描述技能掌握程度时要注意“了解”、“熟悉”、“精通”的区别。

“了解”指只上过课或者看过书,但没做过实际项目,这部分不建议描述过多。

“熟悉”指实际项目中使用某项技术已经较长实际,通过查阅相关文档可以独立解决大部分问题;已经工作过的,再项目开发过程中所用到的技能;对应届生毕业生来说就是毕业设计。

“精通”指对技术使用的得心应手,能很轻松回答这个领域里的绝大多数问题,切记为了修饰成“高人”而轻易使用“精通”,装高手很容易暴露的。

2.1.3 回答“为什么跳槽”

面试官很喜欢问这种问题,主要是考察应聘者的性格,这个基本可以大胆回答,但在回答中少抱怨,也不要流露出负面的情绪,应尽量避免以下4个原因:

  • 老板太苛刻
  • 同事太难相处
  • 加班太频繁:IT行业加班可是家常便饭耶!
  • 工资太低:这块不要和面试官抱怨,面试是为了面试通过;通过后跟HR好好谈

作者给出的答案: 现在的工作做了一段时间,已经没有太多的激情了,因此希望寻找一份更有挑战的工作。然后具体论述为什么有些厌倦现在的职位,以及面试的职位我为什么会感兴趣。

如果我想在现在的职位上得到提升,就必须加强土木行业的学习,可我诸如计算土方量、道路设计等没有太多兴趣,因此出来寻找机会。

我在微软的主要工作是开发xxxx。由于xxxx已经非常成熟,不需要添加多少新功能,因此我的大部分工作是维护和修改Bug。两年下来,调试的能力得到了很大的提高,但长期如此,自己的软件开发和设计能力将得不到提高,因此想出来寻找可以设计和开发系统的职位。同时,在过去几年里的工作都是开发桌面软件,对网络了解甚少,因此希望下一个工作能与网络有关。众所周知,思科是一家网络公司,这里的软件和系统或多或少都离不开网络,因此我对思科的职位很感兴趣。

2.2 技术面试环节

面试官了解应聘者的背景后,接下来就是技术面试了。通常技术面试占用40~50分钟,对面试结果起决定性作用,会关注应聘者的5中素质:

语言细节、链表、树、栈、队列、哈希表、二叉树、二分查找、归并排序、快速排序

边界条件、特殊输入、代码质量、鲁棒性

3中办法分析解决复杂问题:画图、举例、分解

软技能:最近看的书,从中学习了那些新技术

知识迁移能力

2.3 应聘者提问环节

最好能在面试前准备2~3个问题,面试官让应聘者问几个问题,主要是想了解他最关心的问题有哪些。

  • 不要问和自己职位没有关系的问题
  • 不要问薪水
  • 不要打听面试结果

面试前要先对应聘职位或者项目的背景有一定了解:

  • 一是面试前做足功课,收集相关信息,做到对公司成立时间、主要业务、职位要求了然如胸
  • 二是面试中留心面试官说过的话。有不少面试官面试之前会简单介绍相关内容,其中包含其他渠道无法获得信息,项目进展情况等。

1 gcc编译器将c文件翻译成可执行目标文件步骤

预处理阶段、编译阶段、汇编阶段、链接阶段

2 GUN(GNU's Not Unix)

3 了解操作系统益处:

优化程序性能、理解链接时出现的错误、避免安全漏洞

4 系统的硬件组成:

  • 总线

贯穿整个系统的是一组电子管道,称作 总线,它携带信息字节兵负责在各个部件间传递数据

  • I/O设备

I/O(输入/输出)设备是系统与外界世界的联系通道。比如:键盘、鼠标、显示器、磁盘

每个I/O设备都通过一个 控制器适配器与I/O总线相连

  • 主存

主存是一个临时存储设备,在处理器执行程序时,用来存放程序和程序处理的数据。从物理上来说,主存是一组 动态随机存取存储器(DRAM)芯片组成。从逻辑上来说,存储器是一个线性的字节数组,每个字节都有其唯一的地址(数组索引),这些地址是从零开始的

  • 处理器

中央处理单元(CPU),简称 处理器,是解释(或执行)存储在主存中指令的引擎。处理器的核心是一个大小为一个字的 存储设备(或寄存器),成为 程序计数器(PC)

5 执行Hello程序

6 高速缓存

根据机械原理,较大的存储设备要比较小的存储设备运行得慢,而快速设备得造假远高于同类得低速设备

从磁盘驱动器上读取一个字得时间开销要比从主存中读取得开销大1000万倍;类似的处理器从寄存器读取数据要比从主存中读取几乎要快100倍;并且随着半导体技术的进步,这种 处理器与主存之间的差距只会越来越大

针对这种处理器与主存之间的差异,系统设计者采用了更小更快的存储设备,称为 高速缓存存储器(chache memory,简称为chach或高速缓存),作为临时的集结区域,存放处理器近期可能会需要的信息

SRAM: 静态随机访问存储器

7 操作系统管理硬件

程序不直接访问键盘、显示器、磁盘或主存。取而代之由 操作系统提供服务。可以把操作系统看成是应用程序和硬件之间插入的一层软件

操作系统的两个基本功能: 防止硬件被失控的应用程序滥用;向应用程序提供简单一致的机制来控制复杂而又通常大不相同的低级硬件设备

7.1 进程

进程是操作系统对运行程序的一种抽象。在一个系统上可以同时运行多个进程,而每个进程都好像在独占地使用硬件。我们称之为 并发运行,实际上是说一个进程的指令和另一个进程的指令是交错执行的。操作系统实现这种交错执行的机制称之为 上下文切换(context switching)

上下文: 操作系统保存进程运行所需的所有状态信息。比如PC和寄存器文件的当前值、主存的内容

7.2 线程

通常认为一个进程只有单一的控制流,但现代系统中,一个进程实际上可以由多个 线程的执行单元组成,每个线程都运行在进程的上下文中,并共享同样的代码和全局数据

7.3 虚拟内存

这是一个抽象概念,它为每个进程提供一个假象,好像每个进程都在独占地使用内存。每个进程看到的存储器都是一致的,称为 虚拟地址空间

在Linux中,地址是从下往上增大

7.4 文件

文件就是字节序列,仅此而已。每个I/O设备,包括磁盘、键盘、显示器,甚至是网络,都可以看成是文件

系统中的所有输入输出都是通过使用一小组成为Unix I/O的系统函数调用读写文件实现的

8 系统之间利用网络通信

9 Amdahl定律(阿姆达尔定律)

Gene Amdahl,计算领域的早期先锋之一,对提升系统某一部分性能所带来的效果做出了简单且有见地的观察。这个观察被称为Amdahl定律(Amdahl's law)

该定律的主要思想是,当我们对系统的某个部分加速时,其对系统整体性能的影响取决于该部分的重要性和加速程度

若系统执行某应用程序需要时间为$T_{old}$,系统某部分所需执行时间与该时间的比例为$a$ ,而该部分性能提升比例为$k$,即该部分初始所需时间为$aT_{old}$,现所需时间为$(aT_{old}/k)$。因此,总的执行时间应为:

$T_{new} = (1- a)T_{old} + (aT_{old})/k = T_{old}[(1 - a) + a/k]$

由此可计算加速比$S=T_{old}/T_{new}$为:

$S = \frac{1}{(1 - a) + a/k}$

9.1 例子

假设某部分初始耗时比例为60%($a = 0.6$),其加速比例因子为3($k = 3$),则:

$S = \frac{1}{(1 - a) + a/k} = \frac{1}{(1- 0.6) + 0.6/3} = 1.67倍$

表示相对性能

性能提升最好的表示方法就是用上面的$S$

如果有所改进,则值应大于1。我们可以用后缀"x"表示,如2.2x表示2.2倍

9.2 $S$的特殊形式

Amdahl定律有一个有趣的特殊情况:$k$趋近于$\infty$,即将系统某部分加速到花费的时间可以忽略不计:

$S = \frac{1}{(1 - a)}$

例:假设60%的系统加速到几乎不花时间,那么净加速比也只有 1/0.4=2.5x

可以看出,这么高的比例因子只有通过优化系统的大部分组件才能获得

10 并发和并行

并发(concurrency)是一个通用的概念,指一个同时具有多个活动的系统

并行(parallelism)指的是用并发来使一个系统运行得更快

并行可以在计算机系统得多个抽象层次上运用,因此,按系统层次结构中由高到低得顺序重点强调3个层次

1.线程级并发

构建在进程这个抽象上,能够设计出同时有多个程序执行的系统,这导致了并发。传统意义上,这种并发只是模拟出来的,是通过使一台计算机在它正在执行的进程间快速切换实现的,这种称之为 单处理系统。当构建一个由单操作系统内核控制的多处理器组成的系统时,就得到了 多处理器系统,随着 多核处理器超线程(hyperthreading)的出现,这种系统才变得常见

超线程,有时称为 同时多线程(simultaneous multi-threading),是一项允许一个CPU执行多个控制流的技术。

2.指令级并行

在较低的抽象层次上,现代处理器可以同时执行多条指令的属性称为 指令级并行

如果处理器可以打到比一个周期一条指令更快的执行速率,就称之为 超标量(superscalar)处理器

3.单指令、多数据并行

在较低层次上,运行现代处理器拥有特殊的硬件,允许一条指令产生多个可以并行执行的操作,这种方式称之为 单指令、多数据并行即SIMD并行