Files
core/hwe/sammo/Event/Condition/Logic.php
T
Hide_D 8f3c778b80 fix: phan 지시에 따라 일부 버그 수정
- null && key_exists 버그
- or assign이 integer 대상이므로 직접 연산
- false 대신 0 입력한 곳 수정
- 자체 Deprecate 처리한 함수 회피
- 초기화되지 않은 [] 확인하여 처리
- sleep은 정수만 받으므로 usleep으로 변경
- 선언하지 않고 그냥 사용하던 member 변수 선언
- boolean operation 순서 틀린 부분 수정
2021-08-12 23:58:20 +09:00

111 lines
2.8 KiB
PHP

<?php
namespace sammo\Event\Condition;
use sammo\Event\Condition;
class Logic extends \sammo\Event\Condition{
private $mode = 'and';
/** @var \sammo\Event\Condition[] */
private $conditions = [];
const AVAILABLE_LOGIC_NAME = [
'not'=>false,
'and'=>true,
'or'=>true,
'xor'=>true
];
public function __construct(string $mode, ...$conditions){
$mode = strtolower($mode);
if(!array_key_exists($mode, self::AVAILABLE_LOGIC_NAME)){
throw new \InvalidArgumentException('첫번째 인자는 not, and, or, xor 중 하나여야 합니다.');
}
if(!self::AVAILABLE_LOGIC_NAME[$mode] && count($conditions)>1){
throw new \InvalidArgumentException('조건을 하나만 받을 수 있습니다.');
}
$this->mode = $mode;
$this->conditions = array_map(function($condition){
return Condition::build($condition);
}, $conditions);
}
public function eval($env=null){
switch($this->mode){
case 'not':
return $this->logicNot($env);
case 'and':
return $this->logicAnd($env);
case 'or':
return $this->logicOr($env);
case 'xor':
return $this->logicXor($env);
}
throw new \InvalidArgumentException('올바르지 않은 mode.');
}
private function logicNot($env){
$result = self::_eval($this->conditions[0], $env);
$result['value'] = !$result['value'];
$result['chain'][] = 'not';
return $result;
}
private function logicAnd($env){
$value = true;
$chain = [];
foreach($this->conditions as $cond){
$sub = self::_eval($cond, $env);
$chain[] = $sub['chain'];
if(!$sub['value']){
$value = false;
break;
}
}
return [
'value'=>$value,
'chain'=>[$chain, 'and']
];
}
private function logicOr($env){
$value = false;
$chain = [];
foreach($this->conditions as $cond){
$sub = self::_eval($cond, $env);
$chain[] = $sub['chain'];
if($sub['value']){
$value = true;
break;
}
}
return [
'value'=>$value,
'chain'=>[$chain, 'or']
];
}
private function logicXor($env){
$value = false;
$chain = [];
foreach($this->conditions as $cond){
$sub = self::_eval($cond, $env);
$chain[] = $sub['chain'];
$value = ($value != $sub['value']);
}
return [
'value'=>$value,
'chain'=>[$chain, 'xor']
];
}
}