如何写出好代码 – 防御式编程指南

引言

在日常工作当中,大家是否有这种感觉:“好”代码和“差”代码,都可以实现产品的需求。但是不同的人写出的代码,在效率、质量、可维护性、可扩展性、可读性等方面千差万别github开放私库。想法、构思、架构设计得再好,github下载写出来的代码github官网登陆入口三天两头踩坑,这是纸上谈兵。因此软件的健壮性github开放私库是衡量一名工程师水平的github官网登陆入口重要标准。如何提升软件的健壮性?合理的顶层github汤姆设计、完备的测试必不可少,但终其GitHub根本是提升代码质量。

防御式编程是一种安全编码的思维方式。它被看做是减少或消除墨菲定律的一种手段。在程序员奉为圭臬的著作《Code Complete》(代码大全)里,详细介绍了防御式编程。同时国内外有很多大厂把防御式编程作为质量建设的手段之一。本文将介绍防御式编程以及实际场景中如何应用防御式编程。

墨菲定律

如果有github中文官网网页两种或两种以上的方式去做某件事情,而其中一种选择方式将导致灾GitHub难,则必定有人会做出这种选择。这是一种偏悲观的思想,认为所有可能出问题的坏情况都会发生。那么在抱有该想法去做设计github官网登陆入口时,就需要对最坏情况做出预测并采取相对应的措施。同时让使用人员不需要进行复杂的思考,通过直觉即可使用某个系统github官网登陆入口,即所谓的防呆设计。如3.5寸的软盘设计,就设计成只有一种情况可以插入进去。

如何写出好代码 - 防御式编程指南

什么是防御式编程?github中文官网网页

防御式编程,其核心思想是子程序应该不因传入错误数据而被破坏,哪怕是由其他子程序产生的错误数据。简单来说,就是怀疑一切,认为自身代码之外的环境都是不可信的,在这github永久回家地址种情况下,考虑代码该怎么写。

防御式编程和防御式驾驶

防御式编程,这一概念来自防御式驾驶。在防御式驾驶中要建立这样一种思维,那就是你永远也不能确定另一位司机将要做什么。这样才能确保在其他人做出危险动作时你也不会受到伤害。你要承担起保护自己的github中文官网网页责任,哪怕是其他司机犯的错误。

举个实际的场景,以一次SQL查询为例:

Class Main {
    private Connection con = = DriverManager.getConnection(JDBC_URL, JDBC_USER, JDBC_PASSWORD);
    public List<Student> doQuery(String name) {
        Statement stmt = conn.createStatement();
        ResultSet rs = stmt.executeQuery("SELECT id, grade, name, gender FROM students WHERE name=" + name);
        List<Student> studentList = new ArrayList<>();
        while(rs.next()) {
            long id = rs.getLong(1);
            long grade = rs.getLong(2);
            String name = rs.getString(3);
            String gender = convertGender(rs.getInt(4));
            Student student = new Student(id, grade, name, gender);
            studentList.add(student);
        }
        return studentList;
    }
    private String convertGender(int gender) {
        switch(gender) {
            case 0 : return "male";
            case 1 : return "female";
        }
        return null;
    }
}

上述代码比较简单,看上去也实现了我们想要的需求:查询符github是什么合名字的所github永久回家地址有学生。但是有经验的开发同学,就能够发现不少问题,比如:是否正常建立了数据库连接?数据库的返回值有没有做校github中文官网网页验?以上的这些问题总结下github是什么来,我们可以得出防御式编程的关键原则。

边界防御:检查所有的外部输入

在防御式编程的理念中,所有的外部输入都是不可信的,需要校验是否在可允许的范围内。这里需要检查的项包括,空指针、数组越界、不合法入参等。特别是当我们在写一个公共方法时,不确定这个方法会在未来某个时刻,被某个外部系统调用,做好输入检查既能保github直播平台永久回家护自身程序运行的健壮性,又可以让外部系统放心调用。

github中文社区github汤姆面的这个case中有一个明显的传参漏洞,入参name有可能会被外部用户使用SQgithub开放私库L注入攻击,如输入name = “zhangsan or 1 = 1″,就可以github是什么获取所有studgithub是什么ents信息,显然这个是不符合我们要求的入参。

另外这个外部输入不光包括传入参数,还包括任何从方法外部获取到的数据,包括数据库查询到的数据等github是什么

异常处理:在正确性和健壮性之间做好取舍

正确性是指:程序永不返回不准确的结果,即使这样做会不返回结果或是直接退出程序。

健壮性是指:系统在不正常的输入或不正常的外部环境下仍能正常运行,哪怕输出结果是错误的或者不完整的。

正确性和健壮性往往github中文社区是相互矛盾的,当我们检查出错误数据后,还需要决定如何处理github官网它。防御性编程不会掩盖错误,也不会隐藏bug。这需要在健壮性和正确性之间做权衡。在对异常低容忍度的场景,比如火箭发射系统github下载或医疗系github永久回家地址统,正确性要优于健壮性;在github中文社区电商等消费场景中,要优先考虑健壮性,毕竟选择商品不成功,重新刷新一下就好了。

在上述cagithub中文官网网页se中,如果数据库连接失败,比较好的做法是重试或者返github下载回错误码,而不是直接github官网登陆入口让程序退出。

应检尽检:没有完全可靠的外部环境

我们在coding时,会有很多外部方法的调用和交github官网登陆入口互,要对所有的外github是什么部调用保持警惕。这些API或者三方类库也是人写的,人写的就意味着可能有buggithub永久回家地址。一github开放私库种好的思路是尽可能地按照自身逻辑,对github永久回家地址外部调用做检查和异常处理(exception handle)。

在上述case中,存在两个地方的问题:1、github是什么调用数据库并没有检查是否成功;2、调用完数据库并github中文社区没有手动释放资源,这很有可能造成内存泄漏。

显示约束github直播平台永久回家:简单直接的代码风格

在防御式编github开放私库程中,我们提倡使用“最笨”的github中文官网网页方式写代码,尽量少的使用一些语法糖或者隐性规约。

比如很多面试题中都会碰到的”a++ = b++”,是防御式编程当中不提倡的,不如写成”a = b; a++; b++”,虽然代码多了两行,但是意义清晰,且容易理解。

另外一种github是什么情况是使用显示约束。比如:多用const final static,避免使用select *,字段名前加上表名。在上述的casegithub中文社区中,”SELECT id, grade, name, gender FROM students WHERE name=” 里的name应该加上表名: students.name,因为name是mysql中的关键字。

减少依赖:write once, run anywhere

“writegithub永久回家地址 once, run anywhgithub汤姆ere”是Sun公司用来展示Java程序设计语言的跨平台特性的口号,这本身就是一种防御式编程的理github中文官网网页念体现,即在代码中减少对环境的依赖,确保外界环境改变了,程序依然可以正常运行。

在我们的项目中github是什么,比较典型的就是国产化问题。国产化问题经常涉及到数据库的适配,那么在做程序设计时,我们就需要考虑到业务逻辑和底层github是什么数据调用的解耦。

再举一个例子,”i++ != j++” 在不同的编译器中执行结果是不同的,这种也是我们需要避免的。

傻瓜式注释

代码是给系统看的,注github是什么释是给人看的。要想代码具github永久回家地址有比较好的可阅读性,应该把自己当作傻GitHub子去添加注释。(这个和clean code 的理念不同,cgithub下载lean code提倡代码即注释,个人认为这是github汤姆一种理想化的情境)

但注释并不是写废话,好的注释应该出现在:复杂的业务逻辑、非常规的写法、可能有坑的地方、临时解决方案、项目当中核心的类或者方法。写注释是一个优秀工程师必备的技能,大家可以参考下很多优秀项目github官网上的注释写github永久回家地址法。

契约式编程

契约式编程(github下载Contract Programming),顾名思义,在设计阶段就已经确定好每个方法的边界,包括每个方法的参数、返回值,以及它们的类型和所有可能的值。这个术语最早由伯特兰迈耶于1986年提出。他设计了Eiffel程式语言来实现这种程式设计方法,在《物件导向软体建构》(Object-Origithub汤姆ented Software Congithub官网stgithub开放私库ruction)一书中,又提出两个后继版本。

契约式编程强调了三个概念,即前置条件,后置条件和不变式。这几个概念实际上是脱胎于Eiffel语言的一些特性的,不熟悉github汤姆Eiffel的同学GitHub会觉得有点晦涩难懂。

前置条件:期望所有调用它的客户github官网登陆入口模块都保证一定的进入条件,比如非NULL、非0等要求;

后置条件:保证退出时github官网给出特定的属性,比如程序退出时会释放数据库github开放私库连接;

不变式:在进入时假定,并在退出时保持一些特定的属性。

契约式编程是比防御式编程更加乐观的一种编程思路,强调约定和断言,具体想了解契约式编程的同学,可以移步:www.eiffel.com/values/desi…

避免过度设计

过度的防御式编程,也会带来新的问题:

首先是预防不可能会发生的错误,如上面的case所示,对于数据库返回的结果,采用rsgithub中文社区.next()即可判断是否有值,而不需要对rs进行非null判断;

其次,过多的防御式代码,会导致整体程序显得臃肿、难以维护,代码里充斥着大量的判断和非业务代码;同时,程序的性能也会受github直播平台永久回家此影响;

然后,当代码中有非常多的异常捕捉和处理时,可能会导致异常被吞掉,没有正常地报出来。github永久回家地址

总结

防御式编程是一种安全的编程思想,本质上是要求开发人员对代码和线上环境报以辩证的态度和敬畏之心。github永久回家地址它通过以下途径,从而来提升系统健壮性:

  • 提高工程质量——减少bug和问题;
  • 提高源码可读性github是什么—— 源码应该变得可读且可理解,并且能经受code review;
  • 让软件能通过预期的行为来处理不可预期的用户操作。

作为一名优秀的开发者,不能将希望完全寄托于测试,测试驱动开发,github永久回家地址而是在设计、开发GitHub阶段,对系统的异常和边界github直播平台永久回家有充分的认知和考量,这是github开放私库防御式编程带给我们的思考。

附录:防御式编程checkList

一般事github开放私库

  • 子程序是否保护自己免遭有害输入数据的破坏?
  • 你用断言来说明编程假github下载定吗?github开放私库其中包括了前条件和后条件吗?
  • 断言是否只是用来说明从不应该发生的情况?
  • 你是否在架github是什么构或高层设计中规定了github直播平台永久回家一组特定的错误处理技术?
  • 你是否在架构或高层设计中规定了是让错误处github直播平台永久回家理更倾向于健壮性还是正确性?
  • 你是否建立了隔栏来遏制错误可能造成github中文社区的破坏?是否减少了其他需要关注错误处理的代码的数量?
  • 代码中用到辅助调试的代码了吗?
  • 如果需要启用或禁用添加的辅助助手的话,是否无需大动干戈?
  • 在防御式编程时映入的代码量是否适宜–既不过多,也不过少?
  • 在开发阶段是否采用了进攻式编程来使错误难以被忽视?

异常

  • 你在项目中定义了一套标准化的异常处理方案吗?
  • 是否考虑过异常之github中文社区外的其他替代方案?
  • 如果可能的话,是否在github汤姆局部处理了错误而不是把它当成一个异常抛到外部?
  • 代码中是否避github官网免了在构造函数和析构函数中抛出异常?
  • 所有的异常是否都与抛出它们的子程序处于同一抽象层次上?6).每个异常是否都包github官网github中文官网网页了关于异常发生的所有背景信息?
  • 代码中是否没github下载有使用空的catchGitHub语句?(或者如果使用空的catch语句确实很合适,那么明确说明了吗?)

安全事宜

  • 检查有害github开放私库输入数据的代码是否也检查了故意的缓冲区溢出、SQL注入、HTGitHubML注入、证书溢出一级其他恶意输入数据?
  • 是否检查了所有的错误返回码
  • 是否捕获了所有的github汤姆异常?
  • 出错消息中是否避免出现有助于攻击者攻入系统所需的github中文官网网页信息?

要点:

  • 最终产品代码中对错误的处理方式要比“垃圾进,垃圾出”复杂的多。
  • 防御式编程技术可以让错误更容易发现、更容易修改,并减少错误对产品代码的破坏。
  • 断言可以帮github汤姆助人尽早发现错误,尤其是在大型系统和高可靠性的系统中,以及快速变化的代码中。
  • 关于如何处理错误输入的决策是一项GitHub关键的错误处理决策,也是一项关键的高层github是什么设计github下载决策。
  • 异常提供了一种与代码正常流程角度不同的错误处理手段。如果留心使用异常,它可以成为程序员们知识工具箱中的一GitHub项有益补充,同时也应该在异常和其他错误处理手段之间进行权衡比较。
  • 针对产品代码的限制并github是什么不适用于开发中的软件。你可以利用这一优势github直播平台永久回家在开发中添加有助于更快地排查错github中文官网网页误的代码。

作者简介

云智慧架构部,长期致力于智能运维领域工程架构的github开放私库建设和发展,打造高性能、高可用、高易用的运维工程框架,提github汤姆升公司技术水位线。

开源福利

云智慧已开源数据可视化编排平台 FlyFish 。通过配置数据模型为用户提供上百种可视化图形组件,零编码即可实现符合自己业务需求的炫酷可github中文官网网页视化大屏。 同时,飞鱼也提供了灵活的拓展能力,github官网支持组件开发、自定义函数与全局事件等配置, 面向github中文社区复杂需求场景能够保证高效开发与交付。

点击下方地github开放私库址链接,欢迎github下载大家给 FlyFish 点赞github官网登陆入口送 Star。参与组件开发,更有万元现金等你来拿。

  • GitHub 地址: github.com/CloudWise-O…
  • Gitee 地址:gitee.com/CloudWise/f…
  • 万元现金活动github直播平台永久回家: bbs.github中文官网网页aiops.cloudwGitHubise.com/t/Activity

发表回复

提供最优质的资源集合

立即查看 了解详情