WordCountPro,完结撒花

软测第四周作业

一、概述

该项目github地址如下:

https://github.com/YuQiao0303/WordCountPro

该项目需求如下:

http://www.cnblogs.com/ningjing-zhiyuan/p/8654132.html

在此完成了基本任务和拓展任务。

该项目PSP表格如下:

PSP2.1表格
PSP2.1 PSP阶段 预估耗时(分钟) 实际耗时(分钟)
Planning 计划 15 3
· Estimate · 估计这个任务需要多少时间 15 3
Development 开发 930 956
· Analysis · 需求分析 (包括学习新技术) 360 339
· Design Spec · 生成设计文档 60 31
· Design Review · 设计复审 (和同事审核设计文档) 30 0
· Coding Standard · 代码规范 (为目前的开发制定合适的规范) 60 0
· Design · 具体设计 0 0
· Coding · 具体编码 60 130
· Code Review · 代码复审 120 0
· Test · 测试(自我测试,修改代码,提交修改) 240 456
Reporting 报告 305 204
· Test Report · 测试报告 0 0
· Size Measurement · 计算工作量 5 0
· Postmortem & Process Improvement Plan · 事后总结, 并提出过程改进计划 300 204
合计 1250 1163

基本任务

二、实现接口

这次任务设计的框架中,我们设计了一个类,类的结构如下:

经过讨论认为wcPro()相对较难,最终分工如下:

isInputValid() :商莹

wcPro() :余乔(我),雷佳谕。(结对编程)

output():蒋雨晨

其中,我和队友雷佳谕分到的wcPro方法需要完成的功能是,统计文本文件input中的单词和词频,将结果存入类的静态属性Info中。(Info声明如下:)

static TreeMap<String,Integer> Info = new TreeMap<String,Integer>(); `

采用结对编程的方式完成了该方法的实现。设计思路如下:

  • 与第二周相同,采用String类的split方法分割单词,将统计的单词和词频存入TreeMap类型的变量Info中。
  • 按行读取文件。根据需求,输入的文本文件中,所有可能出现的字符分为三种:字母、连字符、其他字符(包括数字和给出的常用字符表中的全部常用字符)。我们将其他字符作为分隔符,分割得到“潜在单词”(word)。
		String reg1 = "[\\s~`!#%\\^&\\*_\\.\\(\\)\\[\\]\\+=:;\"'\\|<>\\,/\\?0-9]+";
String words[] = line.split(reg1);
  • 潜在单词中,可能出现“”(空字符串)和“---”(只含连字符的字符串)的情况。通过判断,直接丢弃改潜在单词。
  for(String word: words){
if("".equals(word)||!word.matches(containLetter)){
continue;
}
...
}
  • 剩下的潜在单词全是需要统计的单词,但统计是需要去掉单词首位的连字符。例如遇到潜在单词“-night”,存入Info的应该是“night”。我们的处理方法是通过循环语句,找到潜在单词word中,第一个不是连字符的字符的坐标firstIndex(也就是第一个字母的坐标),和最后一个不是连字符的字符的坐标lastIndex(也就是最后一个字母的坐标)。然后利用subString方法得到最终要存的单词。
		       String containLetter=".*[a-z].*";
int firstIndex=0,lastIndex=word.length()-1;
char hyphen='-';
//寻找第一个字母的坐标
while(word.charAt(firstIndex)==hyphen){
firstIndex++;
}
//寻找最后一个字母的坐标
while(word.charAt(lastIndex)==hyphen){
lastIndex--;
}
word=word.substring(firstIndex, lastIndex+1);
  • 最后将统计结果写如Info中即可。
 if(!Info.containsKey(word)){
Info.put(word,1);
}
else{
Info.put(word,Info.get(word)+1);
}

于是即可得到wcPro()方法的完整代码:

/**将单词和词频存入info
* 雷佳谕、余乔
* */
static void wcPro(String input) throws IOException{ File file=new File(input);
BufferedReader br = new BufferedReader(new FileReader(file));
String line = null;
//定义一个map集合保存单词和单词出现的个数
//TreeMap<String,Integer> tm = new TreeMap<String,Integer>();
//读取文件
while((line=br.readLine())!=null){
line=line.toLowerCase(); //System.out.println(line);
String reg1 = "[\\s~`!#%\\^&\\*_\\.\\(\\)\\[\\]\\+=:;\"'\\|<>\\,/\\?0-9]+";
String containLetter=".*[a-z].*";
//String reg2 ="\\w+";
//将读取的文本进行分割
String[] words = line.split(reg1);
for(String word: words){
if("".equals(word)||!word.matches(containLetter)){
continue;
} int firstIndex=0,lastIndex=word.length()-1;
char hyphen='-';
//寻找第一个字母的坐标
while(word.charAt(firstIndex)==hyphen){
firstIndex++;
}
//寻找最后一个字母的坐标
while(word.charAt(lastIndex)==hyphen){
lastIndex--;
}
word=word.substring(firstIndex, lastIndex+1);
if(!Info.containsKey(word)){
Info.put(word,1);
}else{
Info.put(word,Info.get(word)+1);
}
} } br.close(); }

设计测试用例

针对结对编写的wcPro()方法的单元测试,是我和队友雷佳谕,分别独立完成的。我们各有一个测试类。

其中,我按照白盒测试和黑盒测试方法,共设计了34个测试用例。

白盒测试

这里采用独立路径测试的思想。

首先画出程序图。原本画出的程序图是这样的:

我和队友画完图,才发现程序结构实在让人看不下去。于是将程序修改之后(也就是刚才展示的样子),才得到新的程序图:

(分支节点用黄色标出)

可以看到,wcPro()方法的环复杂度为7,需要设计七个测试用例。

首先选择了主路径ABCEFGIKLNCAD

之后分别改变A/C/E/G/I/L六个分支节点的判定结果,得到剩下六个独立的测试用例。

最终得到的白盒测试(路经测试)的七个测试用例情况如下:

|Test Case ID 测试用例编号|Test Item 测试项(即功能模块或函数)|Test Case Title 测试用例标题|Test Criticality重要级别|是否自动用例|是否新增修改用例|Pre-condition 预置条件|Input 输入|Procedure 操作步骤|Output 预期结果|Result
实际结果|Status
是否通过|Remark 备注(在此描述使用的测试方法)||

|:--|:--|:--|:--|:--|:--|:--|:--|:--|:--|:--|:--|:--|

|YuTest0|static void wcPro(String input)|主路径|High|是|否|输入文件内容为:“a”|YuTest0.txt|直接执行|Info内容为a:1|Info内容为a:1|OK|路经测试(白盒测试)|

|YuTest1|static void wcPro(String input)|没有行要处理|Low|是|否|输入文件内容为空|YuTest1.txt|直接执行|Info内容为空|Info内容为空|OK|路经测试(白盒测试)|

|YuTest2|static void wcPro(String input)|该行无潜在单词|Low|是|否|输入文件内容为:“a\n\nb”|YuTest2.txt|直接执行|Info内容为a:1.b:1|Info内容为a:1.b:1|OK|路经测试(白盒测试)|

|YuTest3|static void wcPro(String input)|潜在单词为空或不含字母|Low|是|否|输入文件内容为:“-----”|YuTest3.txt|直接执行|Info内容为空|Info内容为空|OK|路经测试(白盒测试)|

|YuTest4|static void wcPro(String input)|潜在单词开头是连字符|Midium|是|否|输入文件内容为:“-a”|YuTest4.txt|直接执行|Info内容为a:1|Info内容为a:1|OK|路经测试(白盒测试)|

|YuTest5|static void wcPro(String input)|潜在单词结尾是连字符|Midium|是|否|输入文件内容为:“a-”|YuTest5.txt|直接执行|Info内容为a:1|Info内容为a:1|OK|路经测试(白盒测试)|

|YuTest6|static void wcPro(String input)|之前出现过该单词|High|是|否|输入文件内容为:“a\n\na”|YuTest6.txt|直接执行|Info内容为a:2|Info内容为a:2|OK|路经测试(白盒测试)|

黑盒测试

wordCountPro到底如何进行黑盒测试,这个问题困扰了我很久。几次推翻重来,最后的考虑是这样的:

输入作为一个文本,每个字符都有很多中可能,文本长度不限,从而文本的内容组合有几乎无数种。

从需求的角度看,只含字母的可以算一类,一串字母首尾含连字符的可以算一类,一串字母中间含连字符的可以算一类,等等。

但是从黑盒测试的角度,假装自己完全不了解程序内部结构,我会非常担心程序能否真的按要求,无bug地把这些情况按照一类来处理。

最后我的选择是,将每个字符分成三类:字母、连字符、其他字符(含数字和特殊字符)。如果将文本长度置为三个字符,27个用例即可穷尽三类字符的所有排列组合,同时也不失一般性。这样测试,我会感到保险很多。

|Test Case ID 测试用例编号|Test Item 测试项(即功能模块或函数)|Test Case Title 测试用例标题|Test Criticality重要级别|是否自动用例|是否新增修改用例|Pre-condition 预置条件|Input 输入|Procedure 操作步骤|Output 预期结果|Result
实际结果|Status
是否通过|Remark 备注(在此描述使用的测试方法)||

|:--|:--|:--|:--|:--|:--|:--|:--|:--|:--|:--|:--|:--|

|YuTest7|static void wcPro(String input)|字母,字母,字母|High|是|否|输入文件内容为:“aaa”|YuTest7.txt|直接执行|Info内容为aaa:1|Info内容为aaa:1|OK|等价类测试(黑盒测试)|

|YuTest8|static void wcPro(String input)|字母,字母,连字符|Low|是|否|输入文件内容为:“aa-”|YuTest8.txt|直接执行|Info内容为aa:1|Info内容为aa:1|OK|等价类测试(黑盒测试)|

|YuTest9|static void wcPro(String input)|字母,字母,其他字符|High|是|否|输入文件内容为:“aa1”|YuTest9.txt|直接执行|Info内容为aa:1|Info内容为aa:1|OK|等价类测试(黑盒测试)|

|YuTest10|static void wcPro(String input)|字母,连字符,字母|High|是|否|输入文件内容为:“a-a”|YuTest10.txt|直接执行|Info内容为a-a:1|Info内容为a-a:1|OK|等价类测试(黑盒测试)|

|YuTest11|static void wcPro(String input)|字母,连字符,连字符|Low|是|否|输入文件内容为:“a--”|YuTest11.txt|直接执行|Info内容为a:1|Info内容为a:1|OK|等价类测试(黑盒测试)|

|YuTest12|static void wcPro(String input)|字母,连字符,其他字符|Low|是|否|输入文件内容为:“a-1”|YuTest12.txt|直接执行|Info内容为a:1|Info内容为a:1|OK|等价类测试(黑盒测试)|

|YuTest13|static void wcPro(String input)|字母,其他字符,字母|High|是|否|输入文件内容为:“a1a”|YuTest13.txt|直接执行|Info内容为a:2|Info内容为a:2|OK|等价类测试(黑盒测试)|

|YuTest14|static void wcPro(String input)|字母,其他字符,连字符|Low|是|否|输入文件内容为:“a1-”|YuTest14.txt|直接执行|Info内容为a:1|Info内容为a:1|OK|等价类测试(黑盒测试)|

|YuTest15|static void wcPro(String input)|字母,其他字符,其他字符|High|是|否|输入文件内容为:“a11”|YuTest15.txt|直接执行|Info内容为a:1|Info内容为a:1|OK|等价类测试(黑盒测试)|

|YuTest16|static void wcPro(String input)|连字符,字母,字母|Low|是|否|输入文件内容为:“-aa”|YuTest16.txt|直接执行|Info内容为aa:1|Info内容为aa:1|OK|等价类测试(黑盒测试)|

|YuTest17|static void wcPro(String input)|连字符,字母,连字符|Low|是|否|输入文件内容为:“-a-”|YuTest17.txt|直接执行|Info内容为a:1|Info内容为a:1|OK|等价类测试(黑盒测试)|

|YuTest18|static void wcPro(String input)|连字符,字母,其他字符|Low|是|否|输入文件内容为:“-a1”|YuTest18.txt|直接执行|Info内容为a:1|Info内容为a:1|OK|等价类测试(黑盒测试)|

|YuTest19|static void wcPro(String input)|连字符,连字符,字母|Low|是|否|输入文件内容为:“--a”|YuTest19.txt|直接执行|Info内容为a:1|Info内容为a:1|OK|等价类测试(黑盒测试)|

|YuTest20|static void wcPro(String input)|连字符,连字符,连字符|Low|是|否|输入文件内容为:“---”|YuTest20.txt|直接执行|Info内容为空|Info内容为空|OK|等价类测试(黑盒测试)|

|YuTest21|static void wcPro(String input)|连字符,连字符,其他字符|Low|是|否|输入文件内容为:“--1”|YuTest21.txt|直接执行|Info内容为空|Info内容为空|OK|等价类测试(黑盒测试)|

|YuTest22|static void wcPro(String input)|连字符,其他字符,字母|Low|是|否|输入文件内容为:“-1a”|YuTest22.txt|直接执行|Info内容为a:1|Info内容为a:1|OK|等价类测试(黑盒测试)|

|YuTest23|static void wcPro(String input)|连字符,其他字符,连字符|Low|是|否|输入文件内容为:“-1-”|YuTest23.txt|直接执行|Info内容为空|Info内容为空|OK|等价类测试(黑盒测试)|

|YuTest24|static void wcPro(String input)|连字符,其他字符,其他字符|Low|是|否|输入文件内容为:“-11”|YuTest24.txt|直接执行|Info内容为空|Info内容为空|OK|等价类测试(黑盒测试)|

|YuTest25|static void wcPro(String input)|其他字符,字母,字母|High|是|否|输入文件内容为:“1aa”|YuTest25.txt|直接执行|Info内容为aa:1|Info内容为aa:1|OK|等价类测试(黑盒测试)|

|YuTest26|static void wcPro(String input)|其他字符,字母,连字符|Low|是|否|输入文件内容为:“1a-”|YuTest26.txt|直接执行|Info内容为a:1|Info内容为a:1|OK|等价类测试(黑盒测试)|

|YuTest27|static void wcPro(String input)|其他字符,字母,其他字符|High|是|否|输入文件内容为:“1a1”|YuTest27.txt|直接执行|Info内容为a:1|Info内容为a:1|OK|等价类测试(黑盒测试)|

|YuTest28|static void wcPro(String input)|其他字符,连字符,字母|Low|是|否|输入文件内容为:“1-a”|YuTest28.txt|直接执行|Info内容为a:1|Info内容为a:1|OK|等价类测试(黑盒测试)|

|YuTest29|static void wcPro(String input)|其他字符,连字符,连字符|Low|是|否|输入文件内容为:“1--”|YuTest29.txt|直接执行|Info内容为空|Info内容为空|OK|等价类测试(黑盒测试)|

|YuTest30|static void wcPro(String input)|其他字符,连字符,其他字符|Low|是|否|输入文件内容为:“1-1”|YuTest30.txt|直接执行|Info内容为空|Info内容为空|OK|等价类测试(黑盒测试)|

|YuTest31|static void wcPro(String input)|其他字符,其他字符,字母|High|是|否|输入文件内容为:“11a”|YuTest31.txt|直接执行|Info内容为a:1|Info内容为a:1|OK|等价类测试(黑盒测试)|

|YuTest32|static void wcPro(String input)|其他字符,其他字符,连字符|Low|是|否|输入文件内容为:“11-”|YuTest32.txt|直接执行|Info内容为空|Info内容为空|OK|等价类测试(黑盒测试)|

|YuTest33|static void wcPro(String input)|其他字符,其他字符,其他字符|Low|是|否|输入文件内容为:“111”|YuTest33.txt|直接执行|Info内容为空|Info内容为空|OK|等价类测试(黑盒测试)|

但是仍然不觉得完全保险:程序真的能将数字和所有提到的特殊字符,都当做一类,进行正确处理吗?

于是还是加了最后一个大综合测试用例,其中包含所有需求文档中提到的常用字符:

|Test Case ID 测试用例编号|Test Item 测试项(即功能模块或函数)|Test Case Title 测试用例标题|Test Criticality重要级别|是否自动用例|是否新增修改用例|Pre-condition 预置条件|Input 输入|Procedure 操作步骤|Output 预期结果|Result
实际结果|Status
是否通过|Remark 备注(在此描述使用的测试方法)||

|:--|:--|:--|:--|:--|:--|:--|:--|:--|:--|:--|:--|:--|

|YuTest34|static void wcPro(String input)|大综合|High|是|否|输入文件内容为:“software Let's
night- night-night -night
"I I" "I"
TABLE1-2
(see Box 3–2).8885d_c01_016
a a a~a`a!a#a%a^a&a*a_a...a.a(a)a[a]a+a=a:a;a"a'a|aa,a/a?a0a1a2a3a4a5a6a7a8a9a”|YuTest34.txt|直接执行|Info内容为:software:1 let:1 s:1 night:2 night-night:1 i:3 table:1 see:1 box:1 d:1 c:1 a:40|Info内容为:software:1 let:1 s:1 night:2 night-night:1 i:3 table:1 see:1 box:1 d:1 c:1 a:40|OK|综合测试|

这样就得到了35个测试用例。

编写测试脚本

测试脚本乏善可陈,唯一值得一提的地方或许在于,我在测试类WCProTestYuQiao的Beforeclass方法中,重写了一遍测试用到的输入文件,从而更好地保证了测试的可移植、可重用性。

@BeforeClass
public static void setUpBeforeClass() throws Exception {
int n=35;
String fileName[] = new String[n];
String fileContent[] = new String[n];
//给文件名赋值
for(int i=0;i<n;i++)
{
fileName[i]="YuQiaoTestFile\\YuTest"+i+".txt";
//System.out.println(fileName[i]);
}
//给文件内容赋值
fileContent[0]="a";
fileContent[1]="";
...

单元测试的结果与评价

几度重新设计用例,重新编写脚本,最终终于得到一条令人满意的green bar:

测试质量

白盒测试的七个测试用例,完全符合独立路径测试的方法和思想,认为完成得很不错。

而黑盒测试部分,可以说我的等价类划分、测试用例设计都只是很大程度上运用了黑盒测试的思想,而非严格遵循其方法。

三种字符,27个用例,其中类似 “-a1”和“1-a”的文本内容,从需求的角度,程序应该作为同一等价类处理。这样的设计,从等价类划分的角度来说,是有冗余的。

但是这里我认为,“程序能否按照需求,对同一等价类内的输入进行等价处理”,本身就是风险的一大来源。因此完全按照需求进行等价类划分来测试,会让我感到风险太大;对不同输入的组合进行测试,结果更有保证。

测试的一大重点,在于低成本和低风险之间的平衡。

而对于wordCountPro这样的小程序,测试的成本和商品软件相比,是极低的(虽然对我个人来说还是下了很大功夫)。用35个用例所耗费的时间和精力,来换取一个更有保障的测试结果,我看性价比挺高,还是值得的。

也就是说,我认为我的测试质量不错。

被测模块质量

测试全部通过,可以认为被测模块较好地实现了功能需求。

拓展任务

考虑到基本任务和拓展任务分别要使用tag打标签,为了保证完成拓展任务时有事可做,我们在完成基本任务时,没有仔细参照代码规范;在拓展任务时,再对照规范进行检查。

规范阅读与理解

选择了阿里巴巴Java开发手册作为参考的规范。主要学习了其中的

  1. 命名风格
  2. 常量定义
  3. 代码格式

    三个部分。

阿里巴巴java开发手册

【强制】类名使用 UpperCamelCase 风格,但以下情形例外: DO / BO / DTO / VO / AO /

PO 等。

正例: MarcoPolo / UserDO / XmlService / TcpUdpDeal / TaPromotion

反例: macroPolo / UserDo / XMLService / TCPUDPDeal / TAPromotion

【强制】方法名、参数名、成员变量、局部变量都统一使用 lowerCamelCase 风格,必须遵从

驼峰形式。

正例: localValue / getHttpMessage() / inputUserId

【强制】常量命名全部大写,单词间用下划线隔开,力求语义表达完整清楚,不要嫌名字长。

正例: MAX_STOCK_COUNT

反例: MAX_COUNT

这几条规则,可以使代码读者看到名称,就知道是类还是变量、方法、常量。

【强制】抽象类命名使用 Abstract 或 Base 开头; 异常类命名使用 Exception 结尾; 测试类 命名以它要测试的类名开始,以 Test 结尾。

这一条可以使代码读者看到类名就知道是否是抽象类、测试类。

【强制】类型与中括号紧挨相连来定义数组。

正例: 定义整形数组 int[] arrayDemo;

反例: 在 main 参数中,使用 String args[]来定义。

变量类型和名称区分得更清晰。

【强制】不允许任何魔法值(即未经预先定义的常量) 直接出现在代码中。

反例: String key = "Id#taobao_" + tradeId;

cache.put(key, value);

更易修改,增强了代码的可维护性。

【强制】大括号的使用约定。如果是大括号内为空,则简洁地写成{}即可,不需要换行; 如果

是非空代码块则:

1) 左大括号前不换行。

2) 左大括号后换行。

3) 右大括号前换行。

4) 右大括号后还有 else 等代码则不换行; 表示终止的右大括号后必须换行。

初见这句左大括号前不换行,我既惊讶又愤怒。

这种方式严重降低了代码的清晰性、可读性和可维护性。

没有清晰的缩进对齐,别说其他人,就是作者本人,编程和修改的过程也会徒增痛苦。

百度了一下,这条规则的主要好处在于,使代码更加紧凑,同样大小的界面可以看到更多行的代码。

行吧行吧你说的对。

队友代码分析

其实我们通过开三场同行评审会的方式,对三个大模块都进行了静态代码检查。

由于其他同学写的模块中,output()相对复杂,这里主要说说,在17161同学的output()方法中,我发现的问题。

可以看到,代码中有许多地方不符合阿里巴巴java开发手册。

第107/111行的左大括号之前换了行;

第114/135行的右大括号后没换行;

第103/104行的类的注释没有采用javadoc规范;

第117行变量writefile命名不符合小驼峰规范;

第123行变量flag命名含义不清晰;

此外,第108行降序排序被写成了升序排列;

总体上注释很少,但由于方法功能简单,可读性仍然很强,不会造成理解障碍。

代码其他变量明明均符合规范,其他大括号换行合理。

静态代码检查工具使用

选择了阿里代码规约检查插件,地址如下:https://p3c.alibaba.com/plugin/eclipse/update

安装方法如下:

https://blog.csdn.net/huangzhe1013/article/details/78248036

出现的问题已经在截图中列出,主要违反了大括号、命名和注释方面的规范。

其中最严重的问题在于if语句后没打大括号:

if(word.equals("")||!word.matches(containLetter))
continue;

于是进行了改进,得到了最终的代码。看到这0 Blockers,0 Criticals ,0 Majors ,真是舒服啊。

重新运行单元测试,没问题:

赏心悦目,赏心悦目。

小组总结

上面的截图没有扫描测试类,如果扫描整个小组含测试类的全部代码,结果如下:

本次小组代码的主要问题,还是在大括号、命名、注释、个别函数使用、数组声明、魔法值等方面违反了代码规范。主要原因是开始编码前,没有仔细研读规范(以方便之后找错并修改)。现在有了这方面意识,也熟悉了常见的不合规范的错误,以后多注意,尽量不再犯。

后记

这次项目经历,让我印象较深的主要是一下两点:

1.先把设计做好,再开始实施。

已经写好测试脚本后,推到重来,重新设计测试用例,非常耗时。

2.一步一步完成一个项目,看着进度条一点一点前进,爽爽的。

3.做项目期间,室友竟然评论我:你最近吃饭怎么这么不积极。

一直信奉“良好的作息是生活高效健康,充满活力”的我,深感这样不好。

以后做项目,也好规律作息,抓紧时间,提高效率。

WordCountPro,完结撒花的更多相关文章

  1. Linux内核分析作业 NO.8 完结撒花~~~

    进程的切换和系统的一般执行过程 于佳心  原创作品转载请注明出处  <Linux内核分析>MOOC课程http://mooc.study.163.com/course/USTC-10000 ...

  2. Alpha 完结撒花 —— 事后诸葛亮

    写在前面 林燊大哥 一路走来,好不容易,终于完结了. 设想和目标 我们的软件要解决什么问题?是否定义得很清楚?是否对典型用户和典型场景有清晰的描述? 解决的问题 用户在进店之前无法得知店铺的优劣,通过 ...

  3. 2019年北航OO第四次博客总结<完结撒花>

    一.UML单元架构设计 1. 类图解析器架构设计 1.1 UML类图 这次作业的目标是要解析一个UML类图,首先为了解耦,我新建了一个类UmTree进行解析工作,而Interaction类仅仅作为实现 ...

  4. 完结撒花!129 集 21 个小时,松哥自制的 Spring Boot2 系列视频教程杀青啦!

    松哥的 Spring Boot 教程分为几个阶段. 2016 松哥最早在 2016 年底的时候开始写 Spring Boot 系列的教程,记得当时在广州上班,年底那段时间在深圳出差,在深圳人生地不熟, ...

  5. 【一起学源码-微服务】Nexflix Eureka 源码十三:Eureka源码解读完结撒花篇~!

    前言 想说的话 [一起学源码-微服务-Netflix Eureka]专栏到这里就已经全部结束了. 实话实说,从最开始Eureka Server和Eureka Client初始化的流程还是一脸闷逼,到现 ...

  6. Beta 完结撒花 —— 事后诸葛亮

    写在前面 林燊大哥 团队成员 短学号 名 2325 燊(队长) 1232 志豪 1131 喜源 2523 宏岩 2230 恺翔 2509 钧昊 2507 俞辛 2501 宇航 2502 柏涛 项目宣传 ...

  7. 算法详解(LCA&RMQ&tarjan)补坑啦!完结撒花(。◕ˇ∀ˇ◕)

    首先,众所周知,求LCA共有3种算法(树剖就不说了,太高级,以后再学..). 1.树上倍增(ST表优化) 2.RMQ&时间戳(ST表优化) 3.tarjan(离线算法)不讲..(后面补坑啦!) ...

  8. Android——仿QQ聊天撒花特效

    实现这样的效果,你要知道贝塞尔曲线,何谓贝塞尔曲线?其实就是曲线,嘿嘿,关于曲线的概念大家可以去 Android绘图机制(二)——自定义View绘制形, 圆形, 三角形, 扇形, 椭圆, 曲线,文字和 ...

  9. Android特效专辑(六)——仿QQ聊天撒花特效,无形装逼,最为致命

    Android特效专辑(六)--仿QQ聊天撒花特效,无形装逼,最为致命 我的关于特效的专辑已经在CSDN上申请了一个专栏--http://blog.csdn.net/column/details/li ...

随机推荐

  1. 15_传智播客iOS视频教程_OC语言完全兼容C语言

    OC支持C语言所有的运算符并且效果是一样的.C语言中所有的运算符OC都支持.这些所有的运算符OC当中全部都支持. 包括C语言的结构体.枚举全部都可以写在OC当中,没有任何问题,并且效果是一样的. 比如 ...

  2. [Swift通天遁地]一、超级工具-(13)使用PKHUD制作各种动态提示窗口

    ★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★➤微信公众号:山青咏芝(shanqingyongzhi)➤博客园地址:山青咏芝(https://www.cnblogs. ...

  3. jwt的应用生成token,redis做储存

    解释一下JWT JWT就是一个字符串,经过加密处理与校验处理的字符串,由三个部分组成.基于token的身份验证可以替代传统的cookie+session身份验证方法.三个部分分别如下: header. ...

  4. HDU4947GCD Array(莫比乌斯反演+树状数组)

    题面 传送门 题解 orz ljz 相当于每一个数要加上 \[v\times [\gcd(i,n)=d]=v\times [\gcd(i/d,n/d)=1]=v\times \sum_{p|{i\ov ...

  5. C#的装箱与拆箱与基本类型

    装箱:值类型转换为对象类型, 实例: int val = 8; object obj = val;//整型数据转换为了对象类型(装箱) 拆箱:之前由值类型转换而来的对象类型再转回值类型, 实例: in ...

  6. 【hdu多校联考第二场】Odd Shops

    Description 这道题的题意是这道难读,大概就是给你n个商店,每个商店的重量为i的商品用ai表示,对于任意商店的a数列都是相同的,重量的范围为[1,10] 求购买方案总数为奇数的重量一共有多少 ...

  7. Windows及Linux环境下Tomcat的JVM参数调优

    Windows环境: catalina.bat文件修改 set JAVA_OPTS=-server -Xms4096m -Xmx4096m -XX:PermSize=512m -XX:MaxPermS ...

  8. Hive insert into directory 命令输出的文件没有列分隔符分析和解决

    参考资料:http://stackoverflow.com/questions/16459790/hive-insert-overwrite-directory-command-output-is-n ...

  9. 循环语言(for)

    循环语句: 给出初始条件,先判断是否满足循环条件,如果不满足条件则跳过for语句,如果满足则进入for语句循环,for语句内的代码执行完毕之后,将按照状态改变改变变量,然后判断是否符合循环条件,符合继 ...

  10. Java常见面试问题: equals()与hashCode()的使用

    目录 1 equals()与'=='的区别 2 equals()方法的重写规则 3 为什么重写equals()的同时还需要重写hashCode() 4 JDK 7中对hashCode()方法的改进 5 ...