大话设计模式-解释器模式


大话设计模式-解释器模式_第1张图片

//声明一个抽象的解释操作,这个接口为抽象语法树中所有的节点所共享。
abstract class AbstractExpression {
	public abstract function interpret(Context $context);
}

//(终结符表达式)实现与文法中的终结符相关联的解释操作。实现抽象表达式中所要求的接口,主要是一个interpret()方法。方法中每一个终结符都有一个具体终结表达式与之相对应。
class TerminalExpression extends AbstractExpression {
	public function interpret(Context $context) {
		echo '终端解释器<br/>';
	}
}

//(非终结符表达式),为文法中的非终结符实现解释操作。对文法中每一条规则R1/R2......Rn都需要一个具体的非终结符表达式类。通过实现抽象表达式的interpret()方法实现解释操作。解释操作以递归方式调用上面所提到的代表R1、R2.。。。。Rn中各个符号的实例变量。
class NonterminalExpression extends AbstractExpression {
	public function interpret(Context $context) {
		echo '非终端解释器<br/>';
	}
}

//包含解释器之外的一些全局信息
class Context {
	private $input;
	private $output;

	public function __get($key) {
		return isset($this->$key) ? $this->$key : null;
	}

	public function __set($key, $value) {
		$this->$key = $value;
	}

}

$context = new Context();
$list[] = new TerminalExpression();
$list[] = new NonterminalExpression();
$list[] = new TerminalExpression();
$list[] = new TerminalExpression();

foreach($list as $exp) {
	$exp->interpret($context);
}

//演奏内容
class PlayContext {
	//演奏文本
	private $text;

	public function __get($key) {
		return isset($this->$key) ? $this->$key : null;
	}

	public function __set($key, $value) {
		$this->$key = $value;
	}
}

//表达式类
abstract class Expression {
	//解释器
	public function interpret(PlayContext $context) {
		if(strlen($context->text) == 0) {
			return;
		}
		//此方法用于当前的演奏文本第一条命令获得命令字母和其参数值。例如‘O 3 E 0.5 G 0.5 A 3’则playKey为O, 而playValue为3
		$playKey = substr($context->text, 0, 1);
		$context->text = substr($context->text, 2);
		$playValue = substr($context->text, 0, strcspn($context->text, ' '));
		$context->text = substr($context->text, strcspn($context->text, ' ') + 1);
		$this->execute($playKey, $playValue);
	}

	//执行
	public abstract function execute($key, $vaule);
}

//音符类
class Note extends Expression {
	public function execute($key, $value) {
		$note = '';
		switch($key) {
		case 'C':
			$note = '1';
			break;
		case 'D':
			$note = '2';
			break;
		case 'E':
			$note = '3';
			break;
		case 'F':
			$note = '4';
			break;
		case 'G':
			$note = '5';
			break;
		case 'A':
			$note = '6';
			break;
		case 'B':
			$note = '7';
			break;
		}
		echo $note;
	}
}

//音符类
class Scale extends Expression {
	public function execute($key, $value) {
		$scale = '';
		switch($value) {
		case '1':
			$scale = '低音';
			break;
		case '2':
			$scale = '中音';
			break;
		case '3':
			$scale = '高音';
			break;
		}
		echo $scale;
	}
}

//音速类
class Speed extends Expression {
	public function execute($key, $value) {
		$speed;
		if($value < 500) {
			$speed = '快速';
		} else if($value >= 1000) {
			$speed = '慢速';
		} else {
			$speed = '中速';
		}

		echo $speed;
	}
}

$context = new PlayContext();
//音乐-上海滩
echo '上海滩<br/>';
$context->text = 'T 500 O 2 E 0.5 G 0.5 A 3 E 0.5 G 0.5 D 3 E 0.5 G 0.5 G 0.5 A 0.5 O 3 C 1 O 2 A 0.5 G 1 C 0.5 E 0.5 D 3 ';
$expression = null;
try {
	while(strlen($context->text) > 0) {
		$str = substr($context->text, 0, 1);
		switch($str) {
		case 'O':
			$expression = new Scale();
			break;
		case 'T':
			$expression = new Speed();
			break;
		case 'C':
		case 'D':
		case 'E':
		case 'G':
		case 'A':
		case 'B':
		case 'P':
			$expression = new Note();
			break;
		}
		if(!empty($expression)) {
			$expression->interpret($context);
		}
	}
} catch (Exception $e) {
	echo $e->getMessage().'<br/>';
}


你可能感兴趣的:(大话设计模式-解释器模式)