策略模式
2020-04-15 本文已影响0人
姜治宇
策略模式,就是把一组算法独立出来单独维护,而不必受模块逻辑的约束。
最典型的策略模式就是表单验证了,大家肯定都经历过重复写if...else验证字段的痛苦,if...else写的代码不仅冗长,而且与dom高度耦合,复用性极差。
我们可以将验证的策略从具体dom分离出来单独维护,解除了二者之间的耦合,代码也会变得非常清爽了。
下面封装一组表单验证逻辑:
var strategy = (function(){
var sy = {//策略对象,私有变量
//原有的策略
notNull:function(value,errorMsg){
value = value.replace(/^\s+|\s+$/,'')
return value ? '' : errorMsg
},
minLen:function(value,len,errorMsg){
return value.length < len ? errorMsg : ''
}
}
return { //提供两个接口,一个是添加策略,一个是验证字段
add:function(type,fn){
sy[type] = fn
},
check:function(type,value,errorMsg){
let args = [...arguments].slice(1)
return sy[type] ? sy[type].apply(this,args) : '没有该类型的策略'
}
}
})()
//添加策略
strategy.add('isEmail',function(value,errorMsg){
value = value.replace(/^\s+|\s+$/,'')
var reg = /^([a-zA-Z]|[0-9])(\w|\-)+@[a-zA-Z0-9]+\.([a-zA-Z]{2,4})$/
return reg.test(value) ? '' : errorMsg
})
//测试一下
console.log(strategy.check('isEmail','hello@163.c','对不起,请输入正确的邮箱'))
console.log(strategy.check('notNull',' ','输入框不可为空'))
放在html测试一下:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>策略模式</title>
</head>
<body>
<form onsubmit="return false">
邮箱:<input type="text" placeholder="请输入邮箱" /><span></span><br>
<button id="sub">提交</button>
</form>
</body>
</html>
<script>
var strategy = (function(){
var sy = {//策略对象,私有变量
//原有的策略
notNull:function(value,errorMsg){
value = value.replace(/^\s+|\s+$/,'')
return value ? '' : errorMsg
},
minLen:function(value,len,errorMsg){
return value.length < len ? errorMsg : ''
}
}
return { //提供两个接口,一个是添加策略,一个是验证字段
add:function(type,fn){
sy[type] = fn
},
check:function(type,value,errorMsg){
let args = [...arguments].slice(1)
return sy[type] ? sy[type].apply(this,args) : '没有该类型的策略'
}
}
})()
//测试
strategy.add('isEmail',function(value,errorMsg){
value = value.replace(/^\s+|\s+$/,'')
var reg = /^([a-zA-Z]|[0-9])(\w|\-)+@[a-zA-Z0-9]+\.([a-zA-Z]{2,4})$/
return reg.test(value) ? '' : errorMsg
})
document.querySelector('#sub').onclick = function(){
var input = document.getElementsByTagName('input')
input[0].nextSibling.textContent = ''
var errMsg = [
strategy.check('isEmail',input[0].value,'邮箱地址错误'),
strategy.check('notNull',input[0].value,'地址不可为空')
]
console.log(errMsg)
errMsg.forEach((val)=>{
input[0].nextSibling.textContent += val
})
}
</script>