带你了解编译原理--用JavaScript实现一个简单的编译器

编译器

编译器能够把一种源语言翻译为语义上等价的另一种目标语言。编译器又分为前端和后端两个部分。前端包括词法分析、语法分析、语义分析、中间代码生成,具有机器无关性。后端包括中间代码优化、目标代码生成,具有机器相关性。

本文实现的目标

主要使用JavaScript实现一个简单的编译器,我们的编译器主要包含词法分析、语法分析、语义分析以及目标代码生成。我们编译器的主要功能为将特定的表达式编译成算数表达式。

编译器的实现

我们首先定义表达式的规则:

  • 函数: mul, sub, sum, div
  • 每个字符串标记都被空格隔开
  • 只支持自然数

表达式的功能为:

  • sum 3 3 编译成 3 + 3
  • sub 3 2 编译成 3 - 2
  • sum 3 sub 3 2 编译成 3 + (3 - 2)
词法分析

词法分析是处理源程序的第一部分,主要任务是逐个扫描输入字符,转换为词法单元(Token)序列,传递给语法分析器进行语法分析。Token 是一个不可分割的最小单元。
根据我们定义的表达式的规则,我们可以得到用于语法分析的单词表

单词符号 编码 助记符
mul 1 $mul -
sub 2 $sub -
sum 3 $sum -
div 4 $div -
自然数 5 $num 数值

根据单词表实现词法分析

// 定义单词表
const words = {
   
  mul: {
    type: '$mul', getValue: () => '-' },
  sub: {
    type: '$sub', getValue: () => '-' },
  sum: {
    type: '$sum', getValue: () => '-' },
  div: {
    type: '$div', getValue: () => '-' },
  num: {
    type: '$num', getValue: (val) => parseInt(val, 10) },
};

function tokenizer(input) {
   

  // `current`变量类似指针,用于记录我们在代码字符串中的位置。
  let current = 0;

  // `tokens`数组是我们放置 token 的地方
  const tokens = [];

  // 首先我们创建一个 `while` 循环, `current` 变量会在循环中自增。
  while (current < input.length) {
   

    // 我们在这里储存了 `input` 中的当前字符
    let char = input[current];

    // 检查是不是空格
    const WHITESPACE = /\s/;
    if (WHITESPACE.test(char)) {
   
      current++;
      continue;
    }

    // 检查是不是数字
    const NUMBERS = /[0-9]/;
    if (NUMBERS.test(char
  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值