这位前辈你好,小弟有些不同的意见
※ 引述《accessdenied (存取违规)》之铭言:
: 单元测试有时候反而破坏程式码的易读性和维护性
: 因为要做到单元测试,就得断开所有的相依性
就算没有单元测试,"高内聚,低耦合"的原则,也应该是适用的
所谓断开相依性更准确地说应该是"相依于抽象而非具体类别"
Design Pattern有80%以上的pattern都是在做这件事
: 而对抗相依性,作法就是引入 DI。但是 DI 就会增加代码阅读和维护的复杂度。
: 举例来说,如果代码内有时间上的相依性,例如用了 DateTime 物件取得现在时间做某些
: 判断,原本可以很简单的写出易于阅读和维护的逻辑:
: If (DateTime.Now > 12:00:00) then return “PM” else return “AM”;
: 为了让单元测试可以控制验证条件,只能
: Interface IDateProvider { virtual GetNow(); }
: Class DateMock : IDateProvider { GetNow() { return 13:00 }
: IDateProvider dateProvider = container.Build(....);
: If (dateProvider.GetNow > 12:00:00) then return “PM” else return “AM”;
: 然后再搞个 config 想办法让程式吃到你写的 DateMock 类别....
: 上面是sudo code 就不用讨论语法细节
以您提的DateTime为例,若If那行出问题,没有单元测试的情况下
我们可能没法马上知道错的是DateTime,还是比较的逻辑(可能是>写成<)
小弟以为单元测试的好处就是在测某个功能时,可以用Mock确保其他东西都是正常的
这样有错误才好抓出来
多加一个IDateProvider有另一个好处是可以应付DateTime不只一种的状况
例如TaiwanDateTime和USDateTime
: 这就是单元测试的代价!程式真的会比较容易阅读吗?
"理想上"的状况是测试程式本身就能明确表达出需求
让人能够只看测试程式而不用去trace又臭又长的商业逻辑就能大概知道整只程式在干嘛
: 单元测试要花在切除相依性的条件花费的成本时间远高于撰写production code
: 而且你的 production code 能不能赚钱还不知道咧?
: 到底需不需要单元测试和 clean code ? 先搞清楚写的用途和目的,你写的东西有没有
: 真正的商业价值再说吧。
商业价值跟有没有单元测试或clean code,应该是没有相关的
总不是说一个本来会赚钱的专案因为写了单元测试就不赚钱了吧?
况且单元测试本身就是为了减少开发与维护成本所出现的东西
: 不要把 clean code 和 TDD 无限上纲了
: 工程师最容易自嗨就是这样,还会自以为“这是专业”?
: 乞丐的乞讨专业比我们强也不会产生“价值”。
就我遇到的状况都是"我们不要搞那些了,程式能动就好"
倒还没听说过因为用TDD,测试程式写太多拖累整个专案的事情...
写出易读、易维护的程式码也是软件工程师的职责之一吧!