程序员基础

© Young 2016-01-26 20:48
Welcome to My GitHub

概念

一、基础概念

1、静态类型语言和动态类型语言

静态类型语言在编译时便已经确定变量的类型,而动态类型语言的变量类型要到程序运行时,待变量被赋予某个值后,才会具有某种类型

静态类型语言的优点首先是在编译时就能发现类型不匹配的错误,编译器可以帮助我们提前避免程序在运行期间有可能发生的一些错误。其次在程序中明确地规定了数据类型,编译器还可以针对这些信息对程序进行一些优化工作,提高程序的执行速度。

动态类型语言的优点是编写的代码数量更少,程序员可以更多的专注于业务逻辑。

静态类型语言做的好的方面既是动态类型语言所欠缺的方面,反之亦然。

2、编译型语言和解释型语言

编译型语言是指在程序执行之前,有一个专门的编译过程的语言,通过编译系统(不仅仅只是通过编译器,编译器只是编译系统的一部分)把高级语言翻译成机器语言,把源高级程序编译成为机器语言文件。

解释型语言是指在运行的时候才翻译的语言,比如VB语言,在执行的时候,专门有一个解释器能够将VB语言翻译成机器语言。

编译型与解释型,两者各有利弊;前者由于程序执行速度快,同等条件下对系统要求较低,因此像开发操作系统、大型应用程序、数据库系统等时都采用它,像C/C++、Pascal/Object Pascal(Delphi)等都是编译语言;而一些网页脚本、服务器脚本及辅助开发接口这样的对速度要求不高、对不同系统平台间的兼容性有一定要求的程序则通常使用解释性语言,如JavaScript、VBScript、Perl、Python、Ruby、MATLAB 等等。

但随着硬件的升级和设计思想的变革,编译型和解释型语言越来越笼统,主要体现在一些新兴的高级语言上,以java与C#举例来说:

JAVA语言是一种编译型-解释型语言,同时具备编译特性和解释特性(其实,确切的说java就是解释型语言,其所谓的编译过程只是将.java文件编程成平台无关的字节码.class文件,并不是向C一样编译成可执行的机器语言,这里需要注意Java中所谓的“编译”和传统的“编译”的区别。

C#语言是编译型语言,但其“编译”过程比较特殊,C#程序在第一次运行的时候,会依赖其.NET Frameworker平台,编译成IL中间码,然后由JIT compiler翻译成本地的机器码执行;第二次再运行相同的程序时,则不需要再执行以上编译和翻译过程,而是直接运行第一次翻译成的机器码;所以对于C#来说,通常第一次运行时间会很长,但从第二次开始,程序的执行时间会快很多。

3、CGI

CGI英文全称是 Common Gateway Interface,通常翻译为通用网关接口,是HTTP服务器与机器上的其他程序进行通信的一个接口。这个“其他程序”可以使用任何计算机语言来编写,它通过CGI这个接口从HTTP服务器取得输入,然后把运行的结果又通过CGI这个接口传给HTTP服务器,而HTTP服务器把这个结果送给浏览器。

CGI是个协议,主要是规定服务器接受到用户请求后用什么格式传哪些参数给CGI程序以及CGI程序处理完之后用什么格式把处理解决返回给服务器。

举例来说,如果请求/index.html,那么web server会去文件系统中找到这个文件,发送给浏览器,这里分发的是静态数据。好了,如果现在请求的是/index.php,根据配置文件,nginx知道这个不是静态文件,需要去找PHP解析器来处理,那么他会把这个请求简单处理后交给PHP解析器。nginx会传哪些数据给PHP解析器呢?url要有吧,查询字符串也得有吧,post数据也要有,http header等,好的,CGI就是规定要传哪些数据、以什么样的格式传递给后方处理这个请求的协议;

当web server收到/index.php这个请求后,会启动对应的CGI程序,这里就是PHP的解析器。接下来PHP解析器会解析php.ini文件,初始化执行环境,然后处理请求,再以CGI规定的格式返回处理后的结果,退出进程,web server再把结果返回给浏览器。

4、FastCGI

FastCGI是语言无关的、可伸缩架构的CGI开放扩展,其主要行为是将CGI解释器进程保持在内存中并因此获得较高的性能,同时还支持分布式的运算。

提高性能,那么CGI程序的性能问题在哪呢?”PHP解析器会解析php.ini文件,初始化执行环境”,就是这里了。标准的CGI对每个请求都会执行这些步骤,所以处理每个时间的时间会比较长,这明显不合理嘛!

那么FastCGI是怎么做的呢?首先,FastCGI会先启一个master,解析配置文件,初始化执行环境,然后再启动多个worker。当请求过来时,master会传递给一个worker,然后立即可以接受下一个请求。这样就避免了重复的劳动,效率自然是高。而且当worker不够用时,master可以根据配置预先启动几个worker等着;当然空闲worker太多时,也会停掉一些,这样就提高了性能,也节约了资源,这就是FastCGI对进程的管理。

5、语法糖

计算机语言中添加的某种语法,这种语法对语言的功能没有影响,但是更方便程序员使用。

6、ORM(Object Relational Mapping)

ORM本身并不是一种具体的产品而是一类框架的总称,它概述了这类框架的基本特征;完成面向对象的程序设计语言到关系数据库的映射,即可利用面向对象程序设计语言的简单易用性,又可利用关系数据库的技术优势。

7、跨域资源共享(CORS)

它允许浏览器向跨源服务器,发出XMLHttpRequest请求,从而克服了AJAX只能同源使用的限制。浏览器一旦发现AJAX请求跨源,会先判断该跨域请求的类型,如果是简单跨域请求就会自动添加一些附加的头信息,如果是复杂跨域请求,则先发送一个预检请求,询问服务器是否允许该跨域请求,一旦服务器通过了”预检”请求,以后每次浏览器正常的CORS请求,就都跟简单请求一样了。

8、单元测试、集成测试、功能测试

测试可以分为单元测试、集成测试、功能测试等多种类型,体现了测试由小到大、由内至外、循序渐进的测试过程和分而治之的思想;

单元测试粒度最小,一般用来表示对开发中的最小可测试单元进行检查和验证,比如C语言中单元指一个函数,Java语言中单元指一个类;

集成测试是单元测试的逻辑扩展,最简单的形式是:把两个已经测试过的单元组合成一个组件,测试它们之间的接口;

功能测试粒度最大,一般采用黑盒的方式对整个功能进行测试。

二、PHP概念

1、PHP-CGI、PHP-FPM

PHP-CGI是PHP的解释器,PHP-CGI只是个CGI程序,他自己本身只能解析请求,返回结果,不会进程管理,所以就出现了一些能够调度PHP-CGI进程的程序也就是PHP-FPM。

从类的角度来说,如果CGI是一种接口,那么FastCGI实现了该接口并进行了一些优化的抽象类,PHP-CGI就是PHP实现的FastCGI类,PHP-FPM就是管理PHP-CGI类的容器

三、JavaScript概念

1、闭包

闭包是一种特殊的对象,它由两部分构成:函数以及创建该函数的环境;也可以简单理解成闭包就是能够读取其它函数内部变量的函数。

在JavaScript语言中,只有函数内部的子函数才能读取局部变量,因此可以把闭包理解成定义在一个函数内部的函数

闭包的主要特征是:一、可以读取函数内部的变量;二、可以让函数内部的局部变量始终保持在内存中,这些特征导致闭包经常被运用到各种高级特性中,比如模拟私有方法、模块化代码等。

需要注意的是大量使用闭包会导致内存消耗很大,网页性能低下,在低版本IE中甚至存在内存泄漏的情况(解决办法是,在退出函数之前,将不使用的局部变量全部删除)。

2、柯里化(Currying)

柯里化是指把接受多个参数的函数变换成接受一个单一参数(最初函数的第一个参数)的函数,并且返回接受余下的参数而且返回结果的新函数的技术。

柯里化这种现象是随着函数被当做一等公民自然而然地产生的,原本与我们需要或不需要无关;仅仅是提供了解决问题的一种思路,另外柯里化方式会创建大量嵌套作用域以及闭包带来一定的性能开销。

柯里化有3个常见作用:1. 参数复用;2. 提前返回;3. 延迟计算/运行。

个人感觉也就提前返回能有点实际作用;

/**
 * 兼容现代浏览器以及IE浏览器的事件添加方法
 */
var addEvent = function(el, type, fn, capture) {
    if (window.addEventListener) {
        el.addEventListener(type, function(e) {
            fn.call(el, e);
        }, capture);
    } else if (window.attachEvent) {
        el.attachEvent("on" + type, function(e) {
            fn.call(el, e);
        });
    } 
};

上边那种写法每次绑定事件都会走一遍if-else判断,其实只用判断一次就可以了,改为柯里化实现为;

var addEvent = (function(){
    if (window.addEventListener) {
        return function(el, sType, fn, capture) {
            el.addEventListener(sType, function(e) {
                fn.call(el, e);
            }, (capture));
        };
    } else if (window.attachEvent) {
        return function(el, sType, fn, capture) {
            el.attachEvent("on" + sType, function(e) {
                fn.call(el, e);
            });
        };
    }
})();

四、安全

1、跨站请求伪造(CSRF)

是一种挟制用户在当前已授权的Web应用程序上执行非本意的操作的攻击方法;

比如如果用户在A网站授权成功,此时不小心访问了危险网站B,B网站要求访问第三方站点A,发出一个请求(前提是该请求本身存在跨域漏洞),此时浏览器处理该请求会带上用户在A网站授权成功的cookie,如果浏览器的Refer机制失效,或者服务器未校验Refer,此时就发生跨站请求伪造攻击;

目前防御CSRF攻击主要有三种策略:验证 HTTP Referer 字段;在请求地址中添加 token 并验证;在 HTTP 头中自定义属性并验证。

五、网络

1、NAT(Network Address Translation)

网络地址转换,当在专用网内部的一些主机本来已经分配到了本地IP地址(即仅在本专用网内使用的专用地址),但现在又想和因特网上的主机通信(并不需要加密)时,可使用NAT方法。

2、WebSocket

WebSocket是一种独立的、创建在单个TCP连接上进行全双工通讯的协议,和HTTP的唯一关联是使用HTTP协议的101状态码进行协议切换,使用的TCP端口是80,可以用于绕过大多数防火墙的限制。

WebSocket使的客户端和服务器之间的数据交换变得更加简单,允许服务器端直接向客户端推送数据而不需要进行请求,在WebSocket API中,浏览器和服务器只需要完成一次握手,两者之间就可以创建持久性的连接,并允许数据进行双向传送。

3、地址解析协议(ARP)

在以太网中,有一种叫作广播的方法,可以把包发给连接在同一以太网中的所有设备,ARP就是利用广播,查询到当前子网中距离目标最近的路由器的MAC地址,如果没有缓存则缓存起来,然后把数据包发送给该路由器,然后该路由器通过路由选择算法,得到下一个路由器并用下一个路由器的MAC地址替换当前数据包的MAC地址,以此类推,直到最后到达目标服务器。

4、网络控制消息协议(ICMP)

它用于TCP/IP网络中发送控制消息,提供可能发生在通信环境中的各种问题反馈,通过这些信息,令管理者可以对所发生的问题作出诊断,然后采取适当的措施解决。

总结

  • 多态最根本的作用就是通过把过程化的条件分支语句转化成对象的多态性,从而消除这些条件分支。

  • 前端国际化原理是通过服务器返回的信息(比如html中lang属性或者window.navigator.language等)加载不同语言的js文件。

  • 大部分最佳实践或者说是一切经验性的知识都是为了帮助人们在不是特别熟悉的情况下就可以上手而不至于犯很严重的错误。

  • 设计模式是对语言不足的补充,很多时候其实都体现了语言的不足。

  • 在实现通过url传某个路径重跳转时,需要对该路径进行安全限制,通过判断host之类的方式,防止钓鱼以及跨站请求伪造等攻击。

  • 合理使用常量机制,编译器会保证在任何情况下值都不会发生变化,这是一种保证代码没有副作用的好方法。

  • 使用private、protected等修饰符来达到信息屏蔽的功能时,大部分情况都是明智的,但是如果滥用,会产生过多的set、get方法,导致代码变得复杂,反而失去了简捷和效率。

发表评论

电子邮件地址不会被公开。 必填项已用*标注