TDD webstrom js git
阅读导航
- TDD+Git 概述
- 问题解析和思考过程
- 测试+实现代码
- 附件说明
TDD+Git 概述
TDD 概述
测试驱动开发(TDD)是一个依赖重复非常短的开发周期的软件开发过程:需求变成非 常具体的测试用例,然后软件只能通过新的测试。
特点描述
大多数传统的程序开发是把问题拿到手后简单分析就开始写代码,着重于在写的过程中遇到问题就去解决,出错就去调试。代码量不大和问题分析不复杂的情况下,这样的方法还是可行和省时。但是当代码量大,问题复杂,细节分支多,需求多时,一旦出错,调试起来很麻烦。还有一个问题就是,不能确保及时提交能编译通过的代码,对版本的控制和追溯会造成混乱。在TDD模式下,由需求和分析后的细节写出测试类别,由测试来驱动开发,这样的好处在于,我们在完成一项测试后能及时反馈对这条测试代码的准确与否。
TDD编码流程
- 分解任务,分出步骤
- 实例化需求,写清需求细节
- 写测试(test.js),只看需求和程序的输入输出不看中间过程
- 写实现(achieve.js),只为当前的需求,用最简单的方式通过即可
- 重构,采用方法消除代码中间冗余和优化代码
- 测试,修复,转3
- 完成
注:一条一条的测试通过,细节划分合理
Git 概述
GIT中是一个版本控制系统用于跟踪的变化(VCS)的计算机文件和协调多人之间的那些文件的工作。它主要用于软件开发,但它可以被用于跟踪中的任何文件的变化。作为分布式修订控制系统它是针对速度,的数据完整性,和用于分布式的,非线性的工作流的支持。
特点描述
- 无摩擦上下文切换。创建一个分支,尝试一个想法,提交几次,切换回分支的地方,应用补丁,切换回您正在尝试的地方,并将其合并。
- 基于角色的编码。有一个分支,总是只包含生产,另一个你合并工作进行测试,和几个较小的日常工作。
- 基于特征的工作流程。为您正在处理的每个新功能创建新的分支,以便您可以无缝地在它们之间切换,然后在该功能合并到主线中时删除每个分支。
- 一次性实验。创建一个分支进行实验,意识到它不会工作,只是删除它 - 放弃工作,没有人看到它(即使你推送其他分支机构)
个人理解:git的使用中我们可以随时回退和查看之前的某一代码版本(前提是曾提交到过代码仓库)以及看每一次版本之前的变化痕迹。初次之外还有一个极大优点,即上面提到的分支结构,可以多次尝试不同的分支并记录结构,之后可按需求进行比较选择。而且这样的话,对代码的过程有很明显的追踪,在维护的时候也很高效。
常用命令
命令 | 示例 | 描述 |
---|---|---|
git init | ~ | 执行git init,当前目录下多一个.git的目录,这个目录是Git来跟踪管理版本 |
git add | git add test.js | 添加add后的文件到暂存区里面去 |
git commit | git commit -m '注释' | 把文件提交到仓库 |
git status | ~ | 查看结果 |
git diff | git diff test.js | 查看修改了什么内容 |
git checkout | git checkout -- file | 可以丢弃工作区的修改 |
git reset | git reset –hard HEAD^ | 直接恢复到上一个版本 |
git log | ~ | 显示从最近到最远的显示日志 |
问题解析和思考过程
*Frequency Number需求:
我想要一个nodejs小程序,它可以帮我处理一段字符串信息,这段字符串信息是由英文单词组成,每两个单词之间有空格,处理结果也为一段字符串,这个字符串应该每行只显示一个单词和它的数量,并且按出现频率倒序排列
按TDD模式来:
- 分解任务,分出步骤
- 实例化需求,写清需求细节
对于复杂问题,可能要一边写一边补充新的用例,但对于这种简单的题目,基本可以提前就想清楚用什么用例驱动去什么产品代码。
大概可以想到如下的用例:
"" => ""
"he" => "he 1",一个单词,驱动出格式化字符串的代码
"he is" => "he 1\r\nis 1",两个不同单词,驱动出分割单词的代码
"he he is" => "he 2\r\nis 1",有相同单词,驱动出分组代码
"he is is" => "is 2\r\nhe 1",驱动出分组后的排序代码
"he is" => "he 1\r\nis 1",多个空格,完善分割单词的代码
后面的步骤按TDD模式走下去,注意重构。在webstrom下本次测试用到的intellij的快捷使用方式已在另一篇文章中列了出来。WebStrom---IntelliJ快捷简单使用
测试+实现代码
/*
* jasmineTest.js @Lizexin
*/
describe("Word Frequency", function () {
it("returns empty string given empty string", function () {
var result = main('');
expect(result).toEqual('');
});
it("returns string given one word", function () {
var result = main('he');
expect(result).toEqual('he 1');
});
it("returns string given two different word", function () {
var result = main('he is');
expect(result).toEqual('he 1\r\nis 1');
});
it("returns string given two duplicated word", function () {
var result = main('he is he');
expect(result).toEqual('he 2\r\nis 1');
});
it("returns string given two duplicated words need to be sorted", function () {
var result = main('he is is');
expect(result).toEqual('is 2\r\nhe 1');
});
it("returns string given two duplicated words splited by multiple spaces", function () {
var result = main('he is');
expect(result).toEqual('he 1\r\nis 1');
});
it("returns string given long string splited by multiple spaces", function () {
var result = main('it was the age of wisdom it was the age of foolishness it is');
expect(result).toEqual('it 3\r\nwas 2\r\nthe 2\r\nage 2\r\nof 2\r\nwisdom 1\r\nfoolishness 1\r\nis 1');
document.write("result:"+"<br>"+result);
});
});
/*
* test.js @Lizexin
*/
var formatWordAndCount = function (word, count) {
return word +
' ' +
count;
};
var group = function (wordArray) {
return wordArray.reduce((array,word)=>{
let entry = array.find((e)=> e.word === word);//找对象
if(entry){
entry.count++;
}else{
array.push({word:word , count:1});
}
return array;
},[]);
};
var split = function (words) {
return words.split(/\s+/);
};
var sort = function (groupWords) {
groupWords.sort((x, y) => y.count - x.count);
};
var format = function (groupWords) {
return groupWords.map((e) => formatWordAndCount(e.word, e.count)).join('\r\n');
};
function main(words){
if(words !== ''){
let wordArray=split(words);
let groupWords = group(wordArray);
sort(groupWords);
return format(groupWords);
}
return ''
}
附件说明
提交过程:
远程库:
Chrome输出:
感谢您花费时间阅读这篇分享,欢迎您的分享和宝贵意见,祝您阅读愉快!
作者 李泽鑫
2017年 4月 18日