وقتی یک برنامه با عبارتها، قوانین، دستورات یا یک زبان ساده و مشخص سروکار دارد، معمولاً خیلی زود با تعداد زیادی شرط و if/else مواجه میشویم.
برای مثال تصور کنید در یک سیستم فروشگاهی میخواهیم قوانینی مانند موارد زیر را بررسی کنیم:
admin AND active
یا:
premium OR manager
یا حتی:
active AND premium AND has_credit
اگر این قوانین را مستقیماً داخل Controller یا Service بنویسیم، با بزرگتر شدن سیستم، مدیریت و توسعه آنها دشوار میشود.
اینجاست که Interpreter Pattern میتواند مفید باشد.
Interpreter Pattern یک Behavioral Design Pattern است که Grammar یک زبان مشخص را به ساختاری از Expressionها تبدیل میکند و سپس هر Expression میتواند با استفاده از یک Context تفسیر شود. در نمونههای PHP، معمولاً یک interpret() در Expressionها وجود دارد و Expressionهای Terminal و Non-Terminal درخت عبارت را تشکیل میدهند.
در این مقاله ابتدا مفهوم Interpreter Pattern را بررسی میکنیم و سپس آن را با PHP از صفر پیادهسازی خواهیم کرد.
Interpreter Pattern چیست؟
Interpreter Pattern الگویی برای پیادهسازی یک زبان یا Grammar ساده است.
در این الگو، قواعد زبان به Objectهای مختلف تبدیل میشوند و هر Object مسئول تفسیر بخش مشخصی از عبارت است.
به زبان ساده:
> به جای اینکه تمام قوانین یک زبان یا عبارت را در یک کلاس بزرگ قرار دهیم، هر Rule یا Expression را به یک Object مستقل تبدیل میکنیم.
برای مثال فرض کنید زبان بسیار سادهای داریم:
A AND B
میتوانیم آن را به ساختاری مانند زیر تبدیل کنیم:
AND
/ \
A B
در این ساختار:
Aیک Terminal Expression است.Bیک Terminal Expression است.ANDیک Non-Terminal Expression است.- کل ساختار یک Expression Tree محسوب میشود.
مستندات DesignPatternsPHP نیز Interpreter را با همین ایده و با کلاسهایی مانند Context، Expression و interpret() نمایش میدهد.
# چرا به Interpreter Pattern نیاز داریم؟
فرض کنید یک سیستم مدیریت دسترسی داریم.
در ابتدا فقط دو قانون داریم:
if ($user->isAdmin() && $user->isActive()) {
// ...
}
اما بعد از مدتی قوانین بیشتری اضافه میشوند:
admin AND active
admin OR manager
premium AND active
premium OR manager
active AND premium AND credit
اگر همه این قوانین را در Controller بنویسیم، کد بهتدریج پیچیده میشود.
مثلاً:
if (
($user->isAdmin() && $user->isActive())
||
($user->isPremium() && $user->hasCredit())
) {
// ...
}
حالا فرض کنید کارفرما بگوید:
premium AND active OR manager
یا:
(admin OR manager) AND active
در این حالت منطق شرطها بهمرور پیچیدهتر میشود.
Interpreter Pattern کمک میکند منطق این Grammar را به Objectهای مختلف تقسیم کنیم.
# ساختار Interpreter Pattern
Interpreter Pattern معمولاً از چند بخش اصلی تشکیل میشود:
Abstract Expression
│
├── Terminal Expression
│
└── Non-Terminal Expression
Context
1. Abstract Expression
این بخش قرارداد مشترک تمام Expressionها را تعریف میکند.
مثلاً:
interface ExpressionInterface
{
public function interpret(Context $context): bool;
}
تمام Expressionهای دیگر باید این متد را پیادهسازی کنند.
2. Terminal Expression
Terminal Expression سادهترین بخش Grammar است.
این Expression دیگر به Expression کوچکتری تقسیم نمیشود.
مثلاً:
admin
active
premium
manager
هرکدام میتوانند یک Terminal Expression باشند.
مثلاً:
class RoleExpression implements ExpressionInterface
{
public function __construct(
private string $role
) {
}
public function interpret(Context $context): bool
{
return $context->hasRole($this->role);
}
}
# 3. Non-Terminal Expression
Non-Terminal Expression از چند Expression دیگر ساخته میشود.
مثلاً:
A AND B
میتواند به شکل زیر پیادهسازی شود:
class AndExpression implements ExpressionInterface
{
public function __construct(
private ExpressionInterface $left,
private ExpressionInterface $right
) {
}
public function interpret(Context $context): bool
{
return $this->left->interpret($context)
&& $this->right->interpret($context);
}
}
در اینجا AndExpression خودش یک Expression است، اما از دو Expression دیگر تشکیل شده است.
# 4. Context چیست؟
Context اطلاعاتی است که Expression برای تفسیر عبارت به آن نیاز دارد.
مثلاً:
class Context
{
public function __construct(
private array $roles = []
) {
}
public function hasRole(string $role): bool
{
return in_array($role, $this->roles, true);
}
}
حالا میتوانیم Context را اینطور بسازیم:
$context = new Context([
'admin',
'active',
]);
# یک مثال ساده از Interpreter Pattern در PHP
بیایید یک سیستم ساده برای بررسی Roleها بسازیم.
فرض کنید میخواهیم بتوانیم چنین عبارتی داشته باشیم:
admin AND active
ساختار پروژه میتواند به شکل زیر باشد:
Context
↓
ExpressionInterface
↓
├── RoleExpression
├── AndExpression
├── OrExpression
└── NotExpression
# مرحله اول: ساخت ExpressionInterface
ابتدا Interface را ایجاد میکنیم:
interface ExpressionInterface
{
public function interpret(Context $context): bool;
}
این Interface میگوید هر Expression باید متد زیر را داشته باشد:
interpret()
و نتیجه آن نیز یک مقدار Boolean باشد.
# مرحله دوم: ساخت Context
حالا Context را میسازیم:
class Context
{
public function __construct(
private array $roles = []
) {
}
public function hasRole(string $role): bool
{
return in_array($role, $this->roles, true);
}
}
# مرحله سوم: ساخت Terminal Expression
حالا Expression مربوط به Role را میسازیم:
class RoleExpression implements ExpressionInterface
{
public function __construct(
private string $role
) {
}
public function interpret(Context $context): bool
{
return $context->hasRole($this->role);
}
}
مثلاً:
$admin = new RoleExpression('admin');
این Expression بررسی میکند که آیا کاربر Role موردنظر را دارد یا خیر.
# مرحله چهارم: ساخت AndExpression
حالا باید بتوانیم دو Expression را با AND ترکیب کنیم:
class AndExpression implements ExpressionInterface
{
public function __construct(
private ExpressionInterface $left,
private ExpressionInterface $right
) {
}
public function interpret(Context $context): bool
{
return $this->left->interpret($context)
&& $this->right->interpret($context);
}
}
حالا میتوانیم بنویسیم:
$expression = new AndExpression(
new RoleExpression('admin'),
new RoleExpression('active')
);
یعنی:
admin AND active
# مرحله پنجم: ساخت OrExpression
برای OR نیز میتوانیم Expression جداگانه داشته باشیم:
class OrExpression implements ExpressionInterface
{
public function __construct(
private ExpressionInterface $left,
private ExpressionInterface $right
) {
}
public function interpret(Context $context): bool
{
return $this->left->interpret($context)
|| $this->right->interpret($context);
}
}
حالا:
$expression = new OrExpression(
new RoleExpression('admin'),
new RoleExpression('manager')
);
یعنی:
admin OR manager
# مرحله ششم: ساخت NotExpression
میتوانیم NOT را نیز اضافه کنیم:
class NotExpression implements ExpressionInterface
{
public function __construct(
private ExpressionInterface $expression
) {
}
public function interpret(Context $context): bool
{
return !$this->expression->interpret($context);
}
}
مثلاً:
$expression = new NotExpression(
new RoleExpression('banned')
);
یعنی:
NOT banned
# اجرای کامل مثال
حالا تمام اجزای سیستم را کنار هم قرار میدهیم:
$context = new Context([
'admin',
'active',
]);
$expression = new AndExpression(
new RoleExpression('admin'),
new RoleExpression('active')
);
$result = $expression->interpret($context);
var_dump($result);
خروجی:
bool(true)
چون Context دارای هر دو Role زیر است:
admin
active
# ساخت Expressionهای پیچیدهتر
قدرت اصلی Interpreter Pattern زمانی مشخص میشود که Expressionها را با یکدیگر ترکیب کنیم.
مثلاً میخواهیم چنین قانونی داشته باشیم:
(admin OR manager) AND active
میتوانیم ابتدا بخش اول را بسازیم:
$adminOrManager = new OrExpression(
new RoleExpression('admin'),
new RoleExpression('manager')
);
سپس آن را با active ترکیب کنیم:
$expression = new AndExpression(
$adminOrManager,
new RoleExpression('active')
);
حالا:
$result = $expression->interpret($context);
ساختار Expression Tree تقریباً به این شکل است:
AND
/ \
OR active
/ \
admin manager
این ساختار یکی از مهمترین مفاهیم Interpreter Pattern است.
# چرا Expression Tree اهمیت دارد؟
وقتی Expressionهای مختلف را داخل یکدیگر قرار میدهیم، در واقع یک ساختار درختی ایجاد میکنیم.
مثلاً:
(admin OR manager) AND active
تبدیل میشود به:
AND
/ \
OR active
/ \
admin manager
هر Node درخت مسئول تفسیر بخش خودش است.
در زمان اجرای:
$expression->interpret($context);
عملیات به شکل زنجیرهای روی Nodeهای درخت اجرا میشود.
نمونههای استاندارد PHP نیز Interpreter را با Expressionهای ترکیبی مانند AndExp و OrExp و متد interpret() پیادهسازی میکنند.
# یک مثال کاربردیتر: سیستم Rule
حالا بیایید مثال را به یک کاربرد نزدیکتر به پروژههای واقعی تبدیل کنیم.
فرض کنید یک فروشگاه اینترنتی داریم و میخواهیم برای کاربران قوانین مختلف تعریف کنیم:
premium AND active
یا:
premium OR vip
میتوانیم Context را به شکل زیر طراحی کنیم:
class UserContext
{
public function __construct(
private array $attributes
) {
}
public function has(string $attribute): bool
{
return $this->attributes[$attribute] ?? false;
}
}
سپس:
class AttributeExpression implements ExpressionInterface
{
public function __construct(
private string $attribute
) {
}
public function interpret(Context $context): bool
{
return $context->has($this->attribute);
}
}
حالا:
$context = new Context([
'premium' => true,
'active' => true,
'vip' => false,
]);
و Expression:
$expression = new AndExpression(
new AttributeExpression('premium'),
new AttributeExpression('active')
);
نتیجه:
var_dump(
$expression->interpret($context)
);
خواهد بود:
bool(true)
# Interpreter Pattern در Laravel
در پروژههای Laravel نیز میتوان از این ایده برای بخشهایی استفاده کرد که با Rule، Expression یا زبان کوچک داخلی سروکار دارند.
برای مثال فرض کنید سیستم تخفیف داریم و مدیر سایت میتواند قوانینی مانند زیر تعریف کند:
customer_is_vip AND order_above_1m
یا:
customer_is_vip OR coupon_valid
میتوانیم Expressionهای مختلف را به کلاسهای مستقل تبدیل کنیم.
مثلاً:
interface DiscountExpression
{
public function interpret(array $data): bool;
}
سپس:
class VipCustomerExpression implements DiscountExpression
{
public function interpret(array $data): bool
{
return $data['is_vip'] ?? false;
}
}
و:
class MinimumOrderExpression implements DiscountExpression
{
public function interpret(array $data): bool
{
return ($data['order_total'] ?? 0) >= 1_000_000;
}
}
حالا:
$expression = new AndExpression(
new VipCustomerExpression(),
new MinimumOrderExpression()
);
و:
$result = $expression->interpret([
'is_vip' => true,
'order_total' => 2_000_000,
]);
# آیا Interpreter برای هر نوع شرطی مناسب است؟
خیر.
این نکته بسیار مهم است.
Interpreter Pattern یکی از الگوهای نسبتاً پیچیده و کمکاربردتر در پروژههای معمولی است و حتی Refactoring.Guru نیز آن را الگویی نسبتاً نادر و پیچیده توصیف کرده است.
اگر فقط چنین شرطی دارید:
if ($user->isAdmin()) {
// ...
}
هیچ دلیلی برای استفاده از Interpreter Pattern وجود ندارد.
حتی اگر چند شرط ساده داشته باشید:
if (
$user->isAdmin()
&& $user->isActive()
) {
// ...
}
باز هم استفاده از Interpreter معمولاً بیش از حد پیچیده است.
Interpreter زمانی ارزش بیشتری پیدا میکند که خود Grammar و Expressionها بخشی از مسئله باشند.
# چه زمانی از Interpreter Pattern استفاده کنیم؟
Interpreter میتواند برای مواردی مانند اینها مناسب باشد:
1. ساخت زبان کوچک
مثلاً یک زبان ساده برای تعریف Rule:
premium AND active
2. Rule Engine
مثلاً:
vip AND order_gt_1m
3. فیلترهای قابل ترکیب
مثلاً:
active AND premium OR manager
4. Queryهای ساده
اگر کاربران بتوانند Query سادهای با Grammar مشخص ایجاد کنند، میتوان آن را به Expression تبدیل کرد.
5. DSL
DSL یا Domain Specific Language به زبان کوچکی گفته میشود که برای یک حوزه مشخص طراحی شده است.
Interpreter میتواند یکی از راههای پیادهسازی چنین سیستمهایی باشد.
# چه زمانی از Interpreter استفاده نکنیم؟
اگر مسئله فقط چند شرط ساده است، از آن استفاده نکنید.
مثلاً این کد:
if ($user->isAdmin() && $user->isActive()) {
return true;
}
نباید صرفاً برای استفاده از Design Pattern تبدیل به چندین کلاس شود.
همچنین اگر Grammar بسیار بزرگ و پیچیده باشد، پیادهسازی دستی Interpreter میتواند به سیستم پیچیدهای تبدیل شود.
در چنین شرایطی ممکن است استفاده از Parserهای تخصصی یا راهکارهای مناسبتر منطقیتر باشد.
# تفاوت Interpreter و Specification Pattern
از آنجا که مقاله قبلی این کلاستر درباره Specification Pattern بود، این دو الگو ممکن است با یکدیگر اشتباه گرفته شوند.
Specification معمولاً روی بیان و ترکیب Business Rule تمرکز دارد.
مثلاً:
Product is active
Product price > 100000
Product stock > 0
و میتوانیم آنها را ترکیب کنیم.
اما Interpreter بیشتر روی تفسیر یک Grammar یا زبان مشخص تمرکز دارد.
برای مثال:
active AND premium
در Interpreter این عبارت میتواند بخشی از یک زبان باشد که باید تفسیر شود.
به همین دلیل اگر فقط Business Rule دارید، Specification معمولاً انتخاب طبیعیتری است؛ اگر واقعاً یک Grammar و Expression Language دارید، Interpreter میتواند مناسبتر باشد.
# تفاوت Interpreter و Strategy Pattern
در Strategy Pattern چند الگوریتم مختلف داریم و میخواهیم یکی از آنها را انتخاب کنیم.
مثلاً:
PaymentStrategy
├── ZarinpalPayment
├── StripePayment
└── PayPalPayment
اما Interpreter درباره تفسیر Expression یا Grammar است.
به شکل ساده:
Strategy
→ کدام الگوریتم را اجرا کنیم؟
Interpreter
→ این عبارت یا زبان را چگونه تفسیر کنیم؟
# تفاوت Interpreter و Visitor Pattern
Interpreter و Visitor نیز میتوانند شبیه یکدیگر به نظر برسند، مخصوصاً زمانی که Expression Tree داریم.
اما هدفشان متفاوت است.
در Interpreter، منطق تفسیر معمولاً در خود Expressionها قرار دارد:
$expression->interpret($context);
در Visitor، عملیات میتواند به یک Visitor جداگانه منتقل شود.
بنابراین اگر روی یک ساختار Expression چند عملیات مستقل مانند:
Evaluate
Export
Validate
Format
داشته باشید، Visitor میتواند انتخاب جالبتری باشد.
# مزایای Interpreter Pattern
مهمترین مزایای این الگو عبارتاند از:
ساختار قابل توسعه
میتوان Expressionهای جدید ایجاد کرد بدون اینکه تمام سیستم را تغییر دهیم.
جداسازی قوانین
هر Rule میتواند کلاس مستقل خودش را داشته باشد.
ترکیب Expressionها
Expressionهای مختلف را میتوان با هم ترکیب کرد.
مثلاً:
(A AND B) OR C
مناسب برای زبانهای کوچک
اگر یک DSL یا زبان ساده دارید، Interpreter میتواند ساختار مناسبی ارائه کند.
# معایب Interpreter Pattern
در کنار مزایا، این الگو معایبی نیز دارد.
افزایش تعداد کلاسها
هر Expression ممکن است یک کلاس جداگانه داشته باشد.
پیچیدگی
اگر Grammar بزرگ شود، مدیریت Expression Tree سختتر میشود.
عملکرد
برای Expressionهای بسیار بزرگ، تفسیر مکرر درخت میتواند هزینه بیشتری داشته باشد.
مناسب نبودن برای همه پروژهها
Interpreter یک Pattern عمومی برای هر نوع شرط نیست.
در پروژههای ساده، استفاده از آن ممکن است باعث Overengineering شود.
# تست Interpreter Pattern با PHPUnit
برای تست میتوانیم یک Context ایجاد کنیم:
$context = new Context([
'admin',
'active',
]);
سپس:
$expression = new AndExpression(
new RoleExpression('admin'),
new RoleExpression('active')
);
و تست:
public function testAdminAndActive(): void
{
$context = new Context([
'admin',
'active',
]);
$expression = new AndExpression(
new RoleExpression('admin'),
new RoleExpression('active')
);
$this->assertTrue(
$expression->interpret($context)
);
}
همچنین میتوانیم حالت False را تست کنیم:
public function testAdminAndManager(): void
{
$context = new Context([
'admin',
]);
$expression = new AndExpression(
new RoleExpression('admin'),
new RoleExpression('manager')
);
$this->assertFalse(
$expression->interpret($context)
);
}
نمونههای DesignPatternsPHP نیز برای Interpreter تستهایی بر اساس ترکیب Expressionها و Context ارائه میکند.
# اشتباهات رایج در استفاده از Interpreter Pattern
اشتباه اول: استفاده برای شرطهای ساده
این کار:
if ($user->isAdmin()) {
}
نیازی به Interpreter ندارد.
اشتباه دوم: ساخت Grammar بدون نیاز واقعی
اگر سیستم شما هیچ زبان یا Expression قابل تفسیر ندارد، استفاده از این Pattern احتمالاً فقط پیچیدگی اضافه ایجاد میکند.
اشتباه سوم: ترکیب نکردن Expressionها به شکل مشخص
اگر Expression Tree طراحی میکنید، ساختار Grammar باید واضح باشد.
مثلاً مشخص باشد:
A AND B
با:
A AND (B OR C)
متفاوت است.
اشتباه چهارم: قرار دادن همه منطق در یک Interpreter بزرگ
اگر تمام منطق را داخل یک کلاس مانند:
class Interpreter
{
// 1000 lines...
}
قرار دهید، عملاً مزیت اصلی Pattern را از دست دادهاید.
هدف Interpreter این است که Grammar و Expressionها را به اجزای مستقل تقسیم کند.
# Interpreter Pattern و امنیت
اگر قرار است کاربر عبارت یا Rule را وارد کند، نباید آن عبارت را مستقیماً به PHP تبدیل و با eval() اجرا کنید.
برای مثال این روش خطرناک است:
eval($userInput);
به جای آن باید Grammar مشخصی داشته باشید و فقط Operatorها و Expressionهایی را که خودتان تعریف کردهاید اجازه دهید.
مثلاً فقط:
AND
OR
NOT
و Expressionهای مشخص:
admin
active
premium
را قبول کنید.
به این ترتیب Interpreter شما فقط زبان محدودی را میپذیرد.
# Interpreter Pattern در PHP؛ یک نمونه کامل
در نهایت میتوانیم مثال را در قالب چند کلاس به شکل زیر جمعبندی کنیم:
<?php
interface ExpressionInterface
{
public function interpret(Context $context): bool;
}
class Context
{
public function __construct(
private array $values = []
) {
}
public function has(string $key): bool
{
return $this->values[$key] ?? false;
}
}
class VariableExpression implements ExpressionInterface
{
public function __construct(
private string $name
) {
}
public function interpret(Context $context): bool
{
return $context->has($this->name);
}
}
class AndExpression implements ExpressionInterface
{
public function __construct(
private ExpressionInterface $left,
private ExpressionInterface $right
) {
}
public function interpret(Context $context): bool
{
return $this->left->interpret($context)
&& $this->right->interpret($context);
}
}
class OrExpression implements ExpressionInterface
{
public function __construct(
private ExpressionInterface $left,
private ExpressionInterface $right
) {
}
public function interpret(Context $context): bool
{
return $this->left->interpret($context)
|| $this->right->interpret($context);
}
}
$context = new Context([
'admin' => true,
'active' => true,
]);
$expression = new AndExpression(
new VariableExpression('admin'),
new VariableExpression('active')
);
var_dump(
$expression->interpret($context)
);
خروجی:
bool(true)
در این مثال:
Context
↓
admin + active
↓
VariableExpression
↓
AndExpression
↓
interpret()
↓
true
# جمعبندی Interpreter Pattern در PHP
Interpreter Pattern یکی از Behavioral Design Patternهای دنیای برنامهنویسی شیگرا است که برای تفسیر یک Grammar یا زبان مشخص استفاده میشود.
در این الگو، Expressionهای مختلف به Object تبدیل میشوند و معمولاً هر Expression دارای متدی مانند:
interpret()
است.
مهمترین اجزای آن عبارتاند از:
- Abstract Expression
- Terminal Expression
- Non-Terminal Expression
- Context
- Client
یکی از مهمترین مزیتهای Interpreter این است که میتوان Expressionها را به صورت درختی ترکیب کرد:
AND
/ \
OR active
/ \
admin manager
اما باید توجه داشت که Interpreter Pattern برای هر نوع شرط یا Validation مناسب نیست. اگر فقط چند شرط ساده دارید، استفاده از آن میتواند باعث پیچیدگی غیرضروری شود.
این Pattern بیشتر زمانی ارزشمند است که برنامه واقعاً با Grammar، Expression، Rule Engine، DSL یا زبان کوچک قابل تفسیر سروکار داشته باشد. مستندات DesignPatternsPHP نیز Interpreter را در دسته Behavioral قرار داده و نمونهای مبتنی بر Expressionهای منطقی و Context ارائه میکند.
# سوالات متداول Interpreter Pattern در PHP
Interpreter Pattern در PHP چیست؟
Interpreter Pattern الگویی از نوع Behavioral است که برای تعریف Grammar یک زبان و تفسیر Expressionهای آن استفاده میشود.
Interpreter Pattern چه زمانی کاربرد دارد؟
زمانی که سیستم با یک زبان کوچک، Expression، Rule Engine، DSL یا مجموعهای از قوانین قابل ترکیب سروکار داشته باشد.
Terminal Expression چیست؟
Terminal Expression بخشی از Grammar است که دیگر به Expression کوچکتری تقسیم نمیشود؛ مانند یک متغیر یا مقدار پایه.
Non-Terminal Expression چیست؟
Non-Terminal Expression از یک یا چند Expression دیگر تشکیل میشود؛ برای مثال:
A AND B
که AND یک Non-Terminal Expression است.
Context در Interpreter Pattern چه کاری انجام میدهد؟
Context اطلاعاتی را نگهداری میکند که Expressionها هنگام تفسیر به آن نیاز دارند.
آیا Interpreter Pattern در Laravel کاربرد دارد؟
بله، مخصوصاً در سیستمهایی که نیاز به Rule Engine، Expressionهای قابل ترکیب یا DSLهای ساده دارند؛ اما برای شرطهای معمولی Laravel بهتر است از راهکارهای سادهتر استفاده شود.
تفاوت Interpreter و Specification چیست؟
Specification بیشتر برای مدلسازی و ترکیب Business Ruleها مناسب است، در حالی که Interpreter روی تعریف و تفسیر Grammar و Expressionهای یک زبان مشخص تمرکز دارد.
آیا Interpreter Pattern همیشه انتخاب مناسبی است؟
خیر. این Pattern نسبتاً پیچیده و کمکاربرد است و اگر مسئله فقط چند شرط ساده باشد، استفاده از آن معمولاً باعث Overengineering میشود.
نتیجه نهایی
اگر در پروژه PHP یا Laravel خود فقط با چند شرط ساده مواجه هستید، نیازی به Interpreter Pattern ندارید. اما اگر قرار است کاربران، مدیر سیستم یا یک بخش دیگر از برنامه بتوانند قوانین و Expressionهای قابل ترکیب را بر اساس یک Grammar مشخص تعریف کنند، Interpreter میتواند معماری بسیار جالبی ایجاد کند.
در چنین شرایطی، به جای ساخت یک if/else بزرگ، میتوان هر بخش از زبان را به یک Expression مستقل تبدیل کرد و در نهایت Expressionها را به شکل یک Tree در کنار یکدیگر قرار داد.





