3 回答
TA贡献1810条经验 获得超4个赞
创建一个包含您要执行的所有验证的数组。数组的每个元素都必须是可调用的。迭代并尽早退出。如果所有验证器都通过了,那就好了。
private function hasValidContent(string $content) : bool
{
$validators = [
// instance method
[$this, 'hasMoreThanOneChar'],
// callable class
new class {
public function __invoke(string $content)
{
return ...;
}
},
// anonymous function
function (string $content): bool {
return ...;
}
];
foreach ($validators as $validate) {
if (!$validate($content)) {
return false;
}
}
return true;
}
TA贡献1876条经验 获得超7个赞
我推断您正在寻找责任链模式。
例如,假设您有三个类:锁、警报和灯,用于检查房屋的状态。
abstract class HomeChecker {
protected $successor;
public abstract function check(Home $home);
public function succeedWith($successor) {
$this->successor = $successor;
}
public function next(Home $home) {
$this->successor->check($home);
}
}
class HomeStatus {
public $locked = true;
public $alarmOn = true;
public $lightsOff = true;
}
class Locks extends HomeChecker {
public function check(Home $home) {
if(!$home->locked) {
throw new Exception('The doors are not locked'); // or basically whatever you want to do
}
$this->next($home);
}
}
class Alarm extends HomeChecker {
public function check(Home $home) {
if(!$home->alarmOn) {
throw new Exception('The Alarms are not on'); // or basically whatever you want to do
}
$this->next($home);
}
}
class Lights extends HomeChecker {
public function check(Home $home) {
if(!$home->lightsOff) {
throw new Exception('The lights are still on!'); // or basically whatever you want to do
}
$this->next($home);
}
}
$locks = new Locks();
$alarm = new Alarm();
$lights = new Lights();
$locks->succeedWith(new Alarm); // set the order in which you want the chain to work
$alarms->succeedWith(new Lights);
$locks->check(new HomeStatus);
所有三个类:Locks、Lights 和 Alarm 都扩展了一个名为HomeChecker的类,该类基本上具有一个抽象检查方法以确保子类确实实现该方法以及两个名为successWith和next 的方法。successWith 方法用于设置一个后继者,如果当前执行的方法返回 true(意味着没有错误),则将调用该后继者。下一个方法本质上调用了链接起来的下一个方法。
通过这一行,我们开始了这个链,如果locks类的check 方法$locks->check(new HomeStatus);中的检查失败,则会抛出一个错误,并且执行将停止,否则它将调用HomeChecker 类的下一个方法,该方法最终将调用 check 方法我们安排的下一堂课
$locks->succeedWith(new Alarm); // set the order in which you want the chain to work
$alarms->succeedWith(new Lights);
在这些行中。
所以通过这种方式我们可以非常优雅地进行链式检查。我希望这能帮到您。
TA贡献1815条经验 获得超10个赞
一个建议是让验证方法抛出 anException而不是返回trueand false(成功时不返回任何内容)。
例如:
Class Validator {
public static function assertString($string) {
if (!is_string($string)) {
throw new Exception('Type mismatch.');
}
}
public static function assertStringLength($string, $min, $max) {
if (strlen($string) < $min || strlen($string) > $max) {
throw new Exception('String outside of length boundaries.');
}
}
}
你的代码看起来像这样:
try {
Validator::assertString($string);
Validator::assertStringLength($string, 4, 50);
} catch (Exception $e) {
// handle invalid input
}
请注意,我的函数是静态的,在这种情况下有意义,但不一定总是如此。
- 3 回答
- 0 关注
- 121 浏览
添加回答
举报