individual program总结2.0
单词存储的思路变化
改变需求之后,编写思路明朗多了,之前单词过滤和单词末尾数字处理的思路总是很乱。
大体没改,只是单词的过滤部分改了些,也优化了些。
首先,过滤单词我用的是根据分隔符分割,分隔符separators = {' ',',','.','<','>','|','\\',')','[',']','{','!','@','#','$','%','^','&','*','(',')','_','+','=','-','}','"'},利用IndexOfAny方法找到分隔符进行分割。循环得到一个个单词。之前就是这样的,但是这部分和单词的asc码值替换以及末尾数字处理是割裂的,没有整体地考虑两个模式下对单词的处理的共性。
为了方便处理单词的排序和扩展模式,我用dictionary类的两个实例wordList<word,value>和wordPatternList<wordPattern,word>存储单词,word是原单词,wordPattern相当于词根。若mode=“SimpleMode”,则wordPatternSimple是转化为小写后的word;若mode=“ExtendedMode”,则wordPatternExtended是转化为小写且取出末尾数字后的word。根据mode的情况,进行wordPattern的赋值,wordPattern=wordPatternSimple or wordPattern=wordPatternExtended。这样,一旦wordPatternList.keycontains(wordPattern),就可比较当下的word和wordPatternList[wordPattern]的ASC码值,进行替换和+1。这一部分我重写之后,代码的重用性就提高了,因为我利用wordPattern根据mode的不同赋值,避免了对替换的讨论。
性能分析
这是对202M的txt文件词频统计的性能分析图
最热路径如下:
可以看到,是IndexOfAny方法的占用最多,这是之前说到的分割单词的一个方法。我认为是对字符串的搜索次数很多而导致的,因为分隔符在英语中极为常见常见的(尤其是空格),而且很多单词比附I,me等都在这里不算作单词,那么这样的分隔便是没有意义的,如果分隔符较少,估计这个算法的性能比较好。