Skip to content

Instantly share code, notes, and snippets.

@bz0
Created July 31, 2018 00:59
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save bz0/b35c0deefed8922c6a70460281434075 to your computer and use it in GitHub Desktop.
Save bz0/b35c0deefed8922c6a70460281434075 to your computer and use it in GitHub Desktop.
GoF Interpreterパターン
<?php
interface Command{
public function execute(Context $context);
}
class JobCommand implements Command{
public function execute(Context $context){
if ($context->getCurrentCommand() !== 'begin'){
throw new RuntimeException('illegal command ' . $context->getCurrentCommand());
}
$command_list = new CommandListCommand();
$command_list->execute($context->next());
}
}
class CommandListCommand implements Command{
public function execute(Context $context){
while(true){
$current_command = $context->getCurrentCommand();
if (is_null($current_command)){
throw new RuntimeException('"end" not found ');
}else if ($current_command === 'end'){
break;
}else{
$command = new CommandCommand();
$command->execute($context);
}
$context->next();
}
}
}
class CommandCommand implements Command{
public function execute(Context $context){
$current_command = $cotext->getCurrentCommand();
if ($current_command === 'diskspace'){
$path = "./";
$free_size = disk_free_space("./");
$max_size = disk_total_space("./");
$ration = $free_size / $max_size * 100;
echo sprintf('Disk Free : %5.1dMB (%3d%%)<br>' .
$free_size / 1024 / 1024,
$ratio
);
}else if ($current_command === 'date'){
echo date('Y/m/d H:i:s') . "<br>";
}else if ($current_command === 'line'){
echo "----------------------<br>";
}else{
throw new RuntimeException('invalid command [' . $current_command . ']');
}
}
}
class Context{
private $commands;
private $current_index = 0;
private $max_index = 0;
public function __construct($command){
$this->commands = split(' +', trim($command));
$this->max_index = count($this->commands);
}
public function next(){
$this->current_index++;
return $this;
}
public function getCurrentCommand(){
if (!array_key_exists($this->current_index, $this->commands)){
return null;
}
return trim($this->commands[$this->current_index]);
}
}
function execute($command){
$job = new JobCommand();
try{
$job->execute(new Context($command));
}catch(Exception $e){
echo htmlspecialchars($e->getMessage(), ENT_QUOTES, mb_internal_encoding());
}
echo "<hr>";
}
$command = <<<STR
<Job>::=begin<CommandList>
<CommandList>::=<Command>*end
<Command>::=diskspace|date|line
STR;
execute($command);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment