>
如何实现此功能
var has = Object.prototype.hasOwnProperty var toString = Object.prototype.toString function isEmpty(val) { if (val == null) return true if ('boolean' == typeof val) return false if ('number' == typeof val) return val === 0 if ('string' == typeof val) return val.length === 0 if ('function' == typeof val) return val.length === 0 if (Array.isArray(val)) return val.length === 0 if (val instanceof Error) return val.message === '' if (val.toString == toString) { switch (val.toString()) { case '[object File]': case '[object Map]': case '[object Set]': { return val.size === 0 } case '[object Object]': { for (var key in val) { if (has.call(val, key)) return false } return true } } } return false } module.exports = isEmpty
我最近给出了一个非常相似的问题的答案,更详细地介绍了认知复杂性是如何工作的(参见https://stackoverflow.com/a/62867219/7730554)。
但总的来说,我认为重要的是要理解,如果有嵌套条件,认知复杂性会增加得更多。这种计算是这样做的,因为人脑可以更好地处理按顺序编写的语句,而不是嵌套的条件。因此,对于每个条件语句(if、switch、for循环等),复杂性值将增加+1。但是对于每一个嵌套条件,在最后一个级别上添加另一个+1。这意味着,if中的if不仅会加+1,还会加+2。一个if,在if里面,在if里面,结果第一个if是+1,第二个if是+2,第三个if是+3。如果您想深入研究这个问题,我建议您看看:https://www.sonarsource.com/docs/cognitiveComplexity.pdf
因此,让我们首先分析方法中的高复杂度值来自哪里:
function isEmpty(val) {
if (val == null) return true // +1
if ('boolean' == typeof val) return false // +1
if ('number' == typeof val) return val === 0 // +1
if ('string' == typeof val) return val.length === 0 // +1
if ('function' == typeof val) return val.length === 0 // +1
if (Array.isArray(val)) return val.length === 0 // +1
if (val instanceof Error) return val.message === '' // +1
if (val.toString == toString) { // +1
switch (val.toString()) { // +2
case '[object File]':
case '[object Map]':
case '[object Set]': {
return val.size === 0
}
case '[object Object]': {
for (var key in val) { // +3
if (has.call(val, key)) return false // +4
}
return true
}
}
}
return false
}
function isEmpty(val) {
if (val == null) return true // +1
if ('boolean' == typeof val) return false // +1
if ('number' == typeof val) return val === 0 // +1
if ('string' == typeof val) return val.length === 0 // +1
if ('function' == typeof val) return val.length === 0 // +1
if (Array.isArray(val)) return val.length === 0 // +1
if (val instanceof Error) return val.message === '' // +1
if (val.toString != toString) { // +1
return false;
}
switch (val.toString()) { // +1
case '[object File]':
case '[object Map]':
case '[object Set]': {
return val.size === 0
}
case '[object Object]': {
for (var key in val) { // +2
if (has.call(val, key)) return false // +3
}
return true
}
}
}
现在,最后一个switch语句可以在if语句之外执行,我们将嵌套级别减少了一个。通过这个简单的改变,认知复杂度现在从17降到了14。
然后,您甚至可以更进一步,通过将返回值提取到一个变量中来更改最后一个case语句,或者从代码块中提取一个单独的方法。这将进一步降低isEmpty()方法的复杂性。
除了提取方法之外,您还可以使用声明性方法,例如数组方法find(),这将进一步降低认知复杂性。
function isEmpty(val) {
if (val == null) return true // +1
if ('boolean' == typeof val) return false // +1
if ('number' == typeof val) return val === 0 // +1
if ('string' == typeof val) return val.length === 0 // +1
if ('function' == typeof val) return val.length === 0 // +1
if (Array.isArray(val)) return val.length === 0 // +1
if (val instanceof Error) return val.message === '' // +1
if (val.toString != toString) { // +1
return false;
}
return checkForComplexTypes(val)
}
function checkForComplexTypes(val) {
var result = null
switch (val.toString()) { // +1
case '[object File]':
case '[object Map]':
case '[object Set]': {
result = val.size === 0
}
case '[object Object]': {
result = Object.keys(val).find(key => has.call(val, key))
}
return result
}
}
在Sonarqube上,我把这个问题作为一个关键问题,有人能帮我解决这个问题吗。这里是代码的详细信息,请让我知道如何用开关情况重构此代码:
如何降低给定代码段的复杂性?我在Sonarqube中得到了这个错误-->重构这个方法,将其认知复杂度从21降低到允许的15。
我得到声纳警告来降低它的复杂性。我如何重构下面的代码,将其认知复杂度从18降低到允许的15?
我在重构这部分代码时遇到了问题。如何降低该代码的认知复杂性
我使用的是SonarQube版本-6.7.7(LTS)和Python language analyzer插件版本-。 成功地完成了声纳分析,然后我可以看到“重构这个功能,将其认知复杂度从17降低到允许的15”相关问题被标记为关键问题。 我觉得这个问题应该归入主要(或)次要类别,但不是关键问题。