关于圈复杂度CCN NCSS

简介:

关于软件度量中的圈复杂度

 
首先看两个概念:
 
NCSS(Non Commenting Source Statements)有效代码行,扣除注释。

CCN(Cyclomatic Complexity Number),圈复杂度。1个方法的CCN值通常意味着我们需要多少个测试案例来覆盖其不同的路径。当CCN发生很大波动或者CCN很高的代码片段被变更时,意味改动引入缺陷风险高。根据资料,圈复杂度(或CC)大于10的方法存在很大的出错风险。

以下内容摘自: http://blog.csdn.net/yefengnidie/article/details/7218993

  一种代码复杂度的衡量标准,中文名称叫做圈复杂度。 在软件测试的概念里,圈复杂度“用来衡量一个模块判定结构的复杂程度,数量上表现为独立现行路径条数,即合理的预防错误所需测试的最少路径条数,圈复杂度 大说明程序代码可能质量低且难于测试和维护,根据经验,程序的可能错误和高的圈复杂度有着很大关系”。圈复杂度大说明程序代码的判断逻辑复杂,可能质量低且难于测试和维护。程序的可能错误和高的圈复杂度有着很大关系。

    控制流图是McCabe复杂度计算的基础,McCabe度量标准是将软件的流程图转化为有向图,然后以图论的知识和计算方法来衡量软件的质量。 McCabe复杂度包括圈复杂度(Cyclomatic complexity)、基本复杂度、模块涉及复杂度、设计复杂度和集成复杂度等。控制流程图分析是一个静态的分析过程,它提供静态的度量标准技术,一般主要运用在白盒测试的方法中 

   有以下三种方法计算圈复杂度: 

  1,流图中区域的数量对应于环型的复杂性; 

  2,给定流图G的圈复杂度V(G),定义为V(G)=E-N+2,E是流图中边的数量,N是流图中结点的数量; 

  3,给定流图G的圈复杂度V(G),定义为V(G)=P+1,P是流图G中判定结点的数量。 

没有流程图的算法: 
      

碰到以下项加 1: 

分支数(如 if、while 和 do while) 

switch 中的 case 语句数 

如果条件是2个复合条件的话 不是加1 是加2 

   面这个实例中,单元测试的覆盖率可以达到100%,但是很容易发现这其中已经漏掉了一个NPE的测试用例。case1方法的圈复杂度为2,因此至少需要2个用例才能完全覆盖到其所有的可能情况。 

    //程序原代码,圈复杂度为 2 

public String case1(int num) { 

       String string = null; 

       if (num == 1) { 

           string = "String"; 

       } 

       return string.substring(0); 

    } 

//上面代码的单元测试代码 

    public void testCase1(){ 

       String test1 = case1(1); 

    } 

e = 3 ; n = 3;那么全复杂度V(G) = 3 - 3 + 2 = 2,既case1的圈复杂度为2。 

  看更复杂的例子 
public String case2(int index, String string) { 

       String returnString = null; 

       if (index < 0) { 

           throw new IndexOutOfBoundsException("exception <0 "); 

       } 

       if (index == 1) { 

           if (string.length() < 2) { 

              return string; 

           } 

           returnString = "returnString1"; 

       } else if (index == 2) { 

           if (string.length() < 5) { 

              return string; 

           } 

           returnString = "returnString2"; 

       } else { 

           throw new IndexOutOfBoundsException("exception >2 "); 

       } 

       return returnString; 

    } 

 
根据公式 V(G) = e – n + 2 = 12 – 8 + 2 = 6 。case2的圈复杂段为6。说明一下为什么n = 8,虽然图上的真正节点有12个,但是其中有5个节点为throw、return,这样的节点为end节点,只能记做一个。 

转载请注明出处:http://www.cnblogs.com/haochuang/ 8年IT工作经验,5年测试技术与管理,2年产品与项目管理,曾参与过云计算\云存储\车联网产品研发工作; 业余自媒体人,有技术类垂直微信公众号;如有招聘或求职方面需求,请Mail to uetest@qq.com ;或通过 QQ:363573922 微博:@念槐聚 联系;

相关文章
|
Java Maven
【异常解决】为什么会产生jar包冲突,如何排查jar包冲突?
【异常解决】为什么会产生jar包冲突,如何排查jar包冲突?
562 0
|
SQL 缓存 Java
数据库治理的探索与实践
本文是 MSE 即将推出的一个数据库治理能力的预告,我们从应用的视角出发整理抽象了我们在访问、使用数据库时场景的一些稳定性治理、性能优化、提效等方面的实战经验,对于每一个后端应用来说,数据库无疑是重中之重,我们希望通过我们的数据库治理能力,可以帮助到大家更好地使用数据库服务。
数据库治理的探索与实践
|
机器学习/深度学习 算法
【2023高教社杯】B题 多波束测线问题 问题分析、数学模型及参考文献
本文介绍了2023年高教社杯数学建模竞赛B题,聚焦于多波束测深系统的覆盖宽度和重叠率问题,包括问题分析、数学模型构建和参考文献,并针对不同场景下的测线设计提出了解决方案。
401 0
【2023高教社杯】B题 多波束测线问题 问题分析、数学模型及参考文献
|
NoSQL Redis
Redis性能优化问题之禁用内存大页,如何解决
Redis性能优化问题之禁用内存大页,如何解决
|
关系型数据库 数据库 PostgreSQL
POSTGRESQL中时间戳的奥秘timestamptz
探索 PostgreSQL 中的时间戳类型:timestamp 代表无时区的时间点,而 timestamptz 包含时区信息,可转换。了解它们的区别对于数据库操作至关重要。使用 `AT TIME ZONE` 关键字可实现两者间的转换。关注木头左,获取更多数据库知识!
POSTGRESQL中时间戳的奥秘timestamptz
|
缓存 编解码 安全
Android经典面试题之Glide的缓存大揭秘
Glide缓存机制包括内存和硬盘缓存。内存缓存使用弱引用的ActiveResources和LRU策略,硬盘缓存利用DiskLruCache。Engine.load方法首先尝试从内存和弱引用池加载,然后从LRU缓存中加载图片,增加引用计数并移出LRU。若缓存未命中,启动新任务或加入现有任务。内存大小根据设备内存动态计算,限制在0.4以下。DiskLruCache使用自定义读写锁,保证并发安全,写操作通过锁池管理,确保高效。
359 0
|
机器学习/深度学习 数据采集 算法
基于Python实现随机森林分类模型(RandomForestClassifier)项目实战
基于Python实现随机森林分类模型(RandomForestClassifier)项目实战
|
数据安全/隐私保护
wpa_supplicant 的使用
wpa_supplicant 的使用
445 1
|
供应链 Kubernetes 安全
SOFAStack软件供应链安全产品解析——SCA软件成分分析
本文将着重介绍针对开源组件风险发现场景的软件供应链安全产品——SCA软件成分分析。
689 2