《Google软件测试之道》笔记

在Google,软件测试团队归属于一个被称为“工程生产力”的中心组织部门,这个部门的职责横跨开发测试人员使用工具的研发、产品发布和各种级别的测试,从单元级别的测试到探索性级别的测试。

Google是一家以创新和速度为基础的公司,快速地发布有用的代码(如果失败,也只有少数早期用户会失望)、迭代地增加早期用户希望使用的功能(最大化用户反馈)。

在整个公司,我们只有非常少的专职测试人员。

Google的测试团队并非雄兵百万,我们更像是小而精的特种部队。

测试人员的稀缺会导致测试资源变得非常昂贵,因此,我们的原则就是让这些稀缺且聪明的测试员工保持昂扬的斗志和充沛的精力。

在Google,写代码的开发人员也承担了质量的重任。质量从来就不仅仅是一些测试人员的问题。在Google,每个写代码的开发者本身就是测试者。

如果你是一名工程师,那么你同时也是一名测试人员。如果在你的职位头衔上有测试的字样,你的任务就是怎样使那些头衔上没有测试的人可以更好地去做测试。

质量不是被测试出来的。如果在最开始设计创建的时候就是错的,那它永远不会变成正确的。从最初的创建阶段就要做正确,否则将会陷入混乱的万丈深渊。

虽然质量不是被测出来的,但同样有证据可以表明,未经测试也不可能开发出有质量的软件。

停止开发与测试的隔离对立。开发和测试应该并肩齐驱。你需要在写完每一段代码后立刻测试这段代码。

测试不是独立隔离的活动,它本身就是开发过程的一部分。

还有谁能比实际写代码的人更适合做测试呢?还有谁能比实际写代码的人更适合去寻找bug呢?如果某个产品出了问题,第一个跳出来的肯定是导致这个问题发生的开发人员,而不是遗漏这个bug的测试人员。

开发人员自己要对自己写的代码负责,比专职的测试人员更适合做测试工作。

测试人员的存在是为了让开发人员的工作更有效率,并且很大一部分体现在避免因马虎粗心而导致的返工。

目的

构建环境,学习 《Linux设备驱动程序》 《Linux内核设计与实现》

Linux环境

Fedora 24,内核版本4.5.5。

Linux 4.5.5-300.fc24.x86_64

下载内核源码

https://www.kernel.org下载了4.19.128版本。

内核配置

使用make help查看所有make选项。

可以使用不同的方法进行配置,比如make configmake menuconfigmake xconfig等。

make xconfig是基于Qt的一个配置工具。

执行make xconfig,按照错误提示安装依赖库。

sudo install gcc-c++ qt qt-devel bison flex
make xconfig

最终在根目录生成.config文件。

编译遇到问题

执行qmake,提示编译器版本太低。

最终决定将Fedora从24升级到30。

升级Fedora

https://www.cnblogs.com/suodingsuiji/p/6288064.html

dnf install dnf-plugin-system-upgrade
dnf system-upgrade download --releasever=25
dnf system-upgrade reboot

- 阅读剩余部分 -

#!/usr/bin/env python3
# -*- coding: utf-8 -*-

import argparse

parser = argparse.ArgumentParser(description="程序描述")

# 互斥组(组内的各参数不能同时使用)
group = parser.add_mutually_exclusive_group()
group.add_argument("-a", "--aaa", help="a参数描述", action="store_true")
group.add_argument("-b", "--bbb", help="b参数描述", type=int)
group.add_argument("-c", "--ccc", help="c参数描述")
args = parser.parse_args()

if args.aaa:
    pass
elif args.bbb:
    pass
elif arg.ccc:
    pass
else:
    parser.print_help()

The Python Standard Library » Generic Operating System Services » argparse — Parser for command-line options, arguments and sub-commands

安装

sudo dnf install gcc python3-devel`
pip install psutil

使用

#!/usr/bin/env python3
# -*- coding: utf-8 -*-

import psutil

# 遍历所有进程,输出进程ID,CPU占比,内存,进程名称
for pid in psutil.pids():
    p = psutil.Process(pid)
    print("{},{},{},{}".format(
        p.pid, p.cpu_percent(), p.memory_info().rss, p.name()));

文档

https://psutil.readthedocs.io/en/latest

《算法(第4版)》笔记

归并

归并排序基于“归并”这个简单的操作,即将两个有序的数组归并成一个更大的有序数组。

要将一个数组排序,可以先(递归地)将它分成两半分别排序,然后将结果归并起来。

// c++
template<class T>
void merge(T& a, int lo, int mid, int hi, T& aux)
{
    // 将a[lo .. mid]和a[mid+1 .. hi]归并
    int i = lo;
    int j = mid + 1;

    for (int k=lo; k<=hi; ++k)
        aux[k] = a[k];

    for (int k=lo; k<=hi; ++k)
    {
        if (i > mid)
            a[k] = aux[j++];
        else if (j > hi)
            a[k] = aux[i++];
        else if (aux[j] < aux[i])
            a[k] = aux[j++];
        else
            a[k] = aux[i++];
    }
}

- 阅读剩余部分 -

《算法(第4版)》笔记

选择排序

首先,找到数组中最小的那个元素,其次,将它和数组的第一个元素交换位置(如果第一个元素就是最小元素那么它就和自己交换)。再次,在剩下的元素中找到最小的元素,将它与数组的第二个元素交换位置。如此往复,直到将整个数组排序。这种方法叫做选择排序,因为它在不断地选择剩余元素之中的最小者。

选择排序的缺点:一个已经有序的数组或是主键全部相等的数组和一个元素随机排列的数组所用的排序时间竟然一样长。

// c++
// 将容器a按升序排列
template<class T>
void selection_sort(T& a)
{
    int n = a.size();
    for (int i=0; i<n; ++i)
    {
        int min = i;
        for (int j=i+1; j<n; ++j)
        {
            if (a[j] < a[min])
                min = j;
        }

        std::swap(a[i], a[min]);
    }
}

- 阅读剩余部分 -


摘自《基督山伯爵》

三个月前,唐戴斯一心只想着自由,现在光有自由不够了,他还渴望财富;要说过错,那不在唐戴斯,而在天主,它限制了人的能力,却给了他无穷的欲望!


至于您,莫雷尔,我要告诉您的秘密是:这个世界上无所谓幸福,也无所谓不幸,有的只是一种境况和另一种境况的比较,如此而已。只有体验过极度不幸的人,才能品尝到极度的幸福。只有下过死的决心的人,马克西米利安,才会知道活着有多好。

幸福地生活下去吧,我心爱的孩子们,请你们永远别忘记,直至天主垂允为人类揭示未来图景的那一天来到之前,人类的全部智慧就包含在这五个字里面:

等待和希望!


摘自《肖申克的救赎》

我当然记得那个小镇的名字,圣华塔尼欧,这名字太美了,令人忘不了。

我发现自己兴奋莫名,颤抖的手几乎握不住笔。我想惟有自由人才能感受到这种兴奋,一个自由人步上漫长的旅程,奔向不确定的未来。

我希望安迪在那儿。

我希望我能成功跨越美墨边界。

我希望能见到我的朋友,和他握握手。

我希望太平洋就和我梦中所见的一样蔚蓝。

我希望……

摘自《Python基础教程》

虽然这里提倡使用原型,但务必对推倒重来持谨慎态度,在你为编写原型投入了不少时间和精力时尤其如此。更好的选择可能是,对原型进行重构和修改,让其变成功能上更好的系统,其原因有多个。

一个可能出现的常见问题是“第二系统综合征”,即力图让第二个版本非常灵巧或完美无缺,导致永远没有完工的时候

“不断重写综合征”在小说创作领域很常见,指的是不断地修改程序,甚至推倒重来。在有些情况下,让程序“还行”可能是最佳的策略——管用就好。

还有“代码疲劳症”,即你对代码逐渐感到厌烦。你花了很长时间来编写代码,却发现它丑陋而笨拙。导致代码看起来粗糙而笨拙的原因之一是,必须处理各种特殊情况并包含多种形式的错误处理等。无论如何,在新版本中也必须包含这些功能,而最初为了实现它们,你可能花了很大的精力(更别说为调试花费的精力了)。

换而言之,如果你觉得原型还有得救,能变成可行的系统,就应竭尽所能地修改它,而不是推倒重来。在本书后面关于开发项目的章节中,我将开发成果分成了界线清晰的两个版本:原型和最终程序。这样做既是出于清晰考虑,也是为了突出通过编写软件的第一个版本获得的经验和洞察力。在实际开发工作中,完全可以先开发原型,再通过重构它来获得最终的系统。

要深入地了解推倒重来的恐怖之处,请参阅Joel Spolsky撰写的文章“Things You Should Never Do, Part I”(joelonsoftware.com)。据Spolsky讲,对所有软件公司来说,推倒重来都是最严重的策略性错误。

以下摘自《敏捷软件开发:原则、模式与实践》。

可持续的开发速度:

软件项目不是全速短跑,它是马拉松长跑。那些一跃过起跑线就开始尽力狂奔的团队将会在远离终点前就筋疲力尽。为了快速地完成开发,团队必须要以一种可持续的速度前进。团队必须保持旺盛的精力和敏锐的警觉。团队必须要有意识地保持稳定、适中的速度。

XP(极限编程)的规则不允许团队加班工作。在版本发布前的一个星期是该规则的唯一例外。如果发布目标就在眼前并且能够一蹴而就,则允许加班。

以下摘自《人月神话》,讨论了开发团队的组建以及运作。

在计算机领域的会议中,常常听到年轻的软件经理声称,他们喜欢由一流人才组成的小型、精干的队伍,而不是那些几百人的大型团队,这里的“人”当然暗指平庸的程序员。其实我们也经常有相同的看法。

软件经理很早就认识到优秀程序员和较差程序员之间生产率的差异。

我常常重复这样一个观点,需要协作沟通的人员数量影响着开发成本,因为成本的主要组成部分是相互的沟通和交流,以及更正沟通不当引起的不良结果(系统调试)。这一点,也暗示系统应该由尽可能少的人员来开发。

如果在一个200人的项目中,有25个最能干和最有开发经验的项目经理,那么开除剩下的175名程序员,让项目经理来编程开发。

- 阅读剩余部分 -

Shader - 着色器,是可以在GPU上运行的程序,分为顶点着色器和片段着色器(像素着色器)。

编写Shader的编程语言主要有三种:

  • GLSL - 用于OpenGL
  • HLSL - 用于Direct3D
  • Cg - 微软和NVIDIA合作开发的,可用于OpenGL和Direct3D

Cg教程:可编程实时图形权威指南

摘自前言

从前,有位咨询顾问造访客户调研其开发项目。系统核心是个类继承体系,顾问看了开发人员所写的一些代码。他发现整个体系相当凌乱,上层超类对于系统的运作做了一些假设,下层子类实现这些假设。但是这些假设并不适合所有子类,导致覆写(override)工作非常繁重。只要在超类做点修改,就可以减少许多覆写工作。在另一些地方,超类的某些意图并未被良好理解,因此其中某些行为在子类内重复出现。还有一些地方,好几个子类做相同的事情,其实可以把它们搬到继承体系的上层去做。

这位顾问于是建议项目经理看看这些代码,把它们整理一下,但是经理并不热衷于此,毕竟程序看上去还可以运行,而且项目面临很大的进度压力。于是经理说,晚些时候再抽时间做这些整理工作。

顾问也把他的想法告诉了在这个继承体系上工作的程序员,告诉他们可能发生的事情。程序员都很敏锐,马上就看出问题的严重性。他们知道这并不全是他们的错,有时候的确需要借助外力才能发现问题。程序员立刻用了一两天的时间整理好这个继承体系,并删掉了其中一半代码,功能毫发无损。他们对此十分满意,而且发现在继承体系中加入新的类或使用系统中的其他类都更快、更容易了。

项目经理并不高兴。进度排得很紧,有许多工作要做。系统必须在几个月之后发布,而这些程序员却白白耗费了两天时间,干的工作与要交付的多数功能毫无关系。原先的代码运行起来还算正常,他们的新设计看来有点过于追求完美。项目要交付给客户的,是可以有效运行的代码,不是用以取悦学究的完美东西。顾问接下来又建议应该在系统的其他核心部分进行这样的整理工作,这会使整个项目停顿一至二个星期。所有这些工作只是为了让代码看起来更漂亮,并不能给系统添加任何新功能。

- 阅读剩余部分 -

CEED: CEGUI Unified Editor

学习OGRE时接触到一个界面库:CEGUI。

CEED是一个CEGUI资源编辑器,使用Python和PySide(Qt for Python)写的。

Qt有两个Python绑定,一个是PyQt,另一个是PySide。

这么优秀的源代码对于学习Python是个不可多得的资源啊,记录一下。

https://bitbucket.org/cegui/ceed

看《程序员的呐喊》、《软件随想录》的时候,大师们常常会提到一门古老的编程语言Lisp。今天有兴趣学习了一下Scheme的语法。Scheme是Lisp的一种方言。

另外,摘一段《软件随想录》中很有意思的一段话:

顺便说一句,我有充分理由在这里说,那些使用grep命令过滤简历的招聘经理真是荒谬可笑。我从来没有见过哪个能用Scheme语言、Haskell语言和C语言中的指针编程的人,竟然不能在两天里面学会Java语言,并且写出的Java程序的质量竟然不能胜过那些有5年Java编程经验的人士。不过,是无法指望人力资源部里那些平庸的懒汉听进去这些话的。

参考:
Scheme 语言概要(上)
Scheme 语言概要(下)
函数式编程初探