Hãy tưởng tượng ví dụ như các hệ thống Bài học phải kết hợp một thành phần đăng ký để thêm bài học mới cho hệ thống. Là một phần của thủ tục đăng ký, một quản trị viên nên được thông báo khi có một bài học được thêm vào. Của hệ thống người dùng không thể đồng ý xem thông báo này phải được gửi qua đường bưu điện, | CHAPTER 11 PERFORMING AND REPRESENTING TASKS will then be passed along to other Expression objects. So that data can be retrieved easily from the Interpretercontext the Expression base class implements a getKey method that returns a unique handle. Let s see how this works in practice with an implementation of Expression abstract class Expression private static keycount 0 private key abstract function interpret InterpreterContext context function getKey if asset this- key self keycount this- key self keycount . return this- key class LiteralExpression extends Expression private value function __construct value this- value value function interpret InterpreterContext context context- replace this this- value class InterpreterContext private expressionstore array function replace Expression exp value this- expressionstore exp- getKey value function lookup Expression exp return this- expressionstore exp- getKey context new InterpreterContext literal new LiteralExpression four literal- interpret context print context- lookup literal . n Here s the output four 192 CHAPTER 11 PERFORMING AND REPRESENTING TASKS I ll begin with the Interpretercontext class. As you can see it is really only a front end for an associative array expressionstore which I use to hold data. The replace method accepts an Expression object as key and a value of any type and adds the pair to expressionstore. It also provides a lookup method for retrieving data. The Expression class defines the abstract interpret method and a concrete getKey method that uses a static counter value to generate store and return an identifier. This method is used by InterpreterContext lookup and InterpreterContext replace to index data. The LiteralExpression class defines a constructor that accepts a value argument. The interpret method requires a InterpreterContext object. I simply call replace using getKey to define the key for retrieval and the value property. This will become a familiar pattern as you examine the other