令牌和lexeme有什么区别?

use*_*873 78 compiler-construction compilation

在Aho Ullman和Sethi的编译器构造中,给出了源程序的输入字符串被分成具有逻辑意义的字符序列,并且被称为标记和词汇是构成令牌的序列所以是什么是基本的区别?

Guy*_*der 108

使用" Compilers Principles,Techniques,&Tools,2nd Ed. " (WorldCat),Aho,Lam,Sethi和Ullman,AKA the Purple Book,

Lexeme pg.111

词汇是源程序中与令牌模式匹配的一系列字符,并由词法分析器识别为该令牌的实例.

令牌pg.111

令牌是由令牌名称和可选属性值组成的对.令牌名称是表示一种词汇单元的抽象符号,例如,特定关键字,或表示标识符的输入字符序列.令牌名称是解析器处理的输入符号.

图案pg.111

模式是令牌的词义可能采用的形式的描述.在关键字作为标记的情况下,模式只是形成关键字的字符序列.对于标识符和一些其他标记,模式是更复杂的结构,由许多字符串匹配.

图3.2:令牌的示例pg.112

[Token]       [Informal Description]                  [Sample Lexemes]
if            characters i, f                         if
else          characters e, l, s, e                   else
comparison    < or > or <= or >= or == or !=          <=, !=
id            letter followed by letters and digits   pi, score, D2
number        any numeric constant                    3.14159, 0, 6.02e23
literal       anything but ", surrounded by "'s       "core dumped"
Run Code Online (Sandbox Code Playgroud)

为了更好地理解与词法分析器和解析器的这种关系,我们将从解析器开始并向后工作到输入.

为了更容易设计解析器,解析器不能直接使用输入,而是接收词法分析器生成的标记列表.查看图3.2令牌列,我们看到令牌如if,else,comparison,id,numberliteral; 这些是令牌的名称.通常使用词法分析器/解析器,令牌是一种结构,它不仅包含令牌的名称,还包含构成令牌的字符/符号以及构成令牌的字符串的起始和结束位置,开始和结束位置用于错误报告,突出显示等.

现在,词法分析器接受字符/符号的输入,并使用词法分析器的规则将输入的字符/符号转换为标记.现在,使用词法分析器/解析器的人对他们经常使用的东西有自己的话.您认为构成令牌的一系列字符/符号是使用词法分析器/解析器调用lexeme的人.因此,当您看到lexeme时,只需考虑表示令牌的一系列字符/符号.在比较例中,文字/符号的序列可以是不同的模式,例如<>else3.14

另一种思考二者之间关系的方法是,令牌是解析器使用的编程结构,它具有一个名为lexeme的属性,用于保存输入中的字符/符号.现在,如果您查看代码中令牌的大多数定义,您可能看不到lexeme作为令牌的属性之一.这是因为令牌更可能保持表示令牌和词位的字符/符号的开始和结束位置,因为输入是静态的,所以可以根据需要从开始和结束位置导出字符/符号序列.

  • 在口语编译器的使用中,人们倾向于交替使用这两个术语.如果您需要它,精确的区别是很好的. (11认同)

小智 31

当源程序被送入词法分析器时,它首先将字符分解为词汇序列.然后将词汇用于构造令牌,其中词汇被映射到令牌中.名为myVar的变量将映射到表示< id,"num"> 的标记,其中"num"应指向变量在符号表中的位置.

不久之后:

  • Lexemes是从字符输入流派生的单词.
  • 标记是映射到令牌名称和属性值的词位.


一个例子包括:
x = a + b*2
产生词位:{x,=,a,+,b,*,2}
使用相应的标记:{< id,0>,<=>,< id,1 >,<+>,< id,2>,<*>,< id,3>}

  • 它应该是<id,3>吗?因为2不是标识符 (2认同)

Raj*_*att 7

词素-词素是源程序中与标记模式匹配的字符序列,并被词法分析器识别为该标记的实例。

令牌- 令牌是由令牌名称和可选令牌值组成的一对。令牌名称是词汇单元的一个类别。常见的令牌名称是

  • 标识符:程序员选择的名称
  • 关键字:编程语言中已有的名称
  • 分隔符(也称为标点符号):标点符号和成对分隔符
  • 运算符:对参数进行运算并产生结果的符号
  • 文字:数字、逻辑、文本、参考文字

考虑编程语言 C 中的这个表达式:

总和 = 3 + 2;

标记化并由下表表示:

 Lexeme        Token category
------------------------------
sum      |    Identifier
 =       |    Assignment operator
 3       |    Integer literal
 +       |    Addition operator
 2       |    Integer literal
 ;       |    End of statement
Run Code Online (Sandbox Code Playgroud)


cod*_*nza 7

词位- 词位是一串字符,是编程语言中最低级别的句法单元。

标记- 标记是一个句法类别,它形成一个词素类,这意味着词素属于哪个类,它是关键字、标识符还是其他任何东西。词法分析器的主要任务之一是创建一对词素和标记,即收集所有字符。

让我们举个例子:-

如果(y<= t)

y=y-3;

词素令牌

如果关键字

( 左括号

y 标识符

< = 比较

t 标识符

) 右括号

y 标识符

= 分配

y 标识符

_ 算术

3 整数

;                                    分号

Lexeme 和 Token 的关系

lexeme 和 token 的关系


小智 6

a)代币是构成程序文本的实体的符号名称; 例如,对于关键字if,以及任何标识符的id.这些构成了词法分析器的输出.五

(b)模式是一种规则,规定输入中的一系列字符何时构成一个标记; 例如,令牌if的序列i,f,以及以令牌id的字母开头的任何字母数字序列.

(c)词汇是输入中与模式匹配的一系列字符(因此构成一个标记的实例); 例如,如果匹配if的模式,并且foo123bar匹配id的模式.


小智 6

LEXEME - 形成TOKEN的PATTERN匹配的字符序列

PATTERN - 定义TOKEN的规则集

TOKEN - 编程语言ex的字符集上有意义的字符集合:ID,常量,关键字,运算符,标点符号,文字字符串


小智 5

令牌:(关键字,标识符,标点符号,多字符运算符)的种类,简单地说,是一个令牌。

模式:从输入字符形成标记的规则。

Lexeme :它是 SOURCE PROGRAM 中与令牌模式匹配的字符序列。基本上,它是Token的一个元素。


小智 5

令牌: 令牌是可以被视为单个逻辑实体的字符序列。典型的标记是,
1) 标识符
2) 关键字
3) 运算符
4) 特殊符号
5) 常量

模式:输入中的一组字符串,为其生成相同的标记作为输出。这组字符串由称为与令牌关联的模式的规则描述。
词位:词位是源程序中与标记模式匹配的字符序列。


May*_*ula 5

让我们看看词法分析器(也称为 Scanner )的工作

让我们举一个例子表达式:

INPUT : cout << 3+2+3;

FORMATTING PERFORMED BY SCANNER :  {cout}|space|{<<}|space|{3}{+}{2}{+}{3}{;} 
Run Code Online (Sandbox Code Playgroud)

虽然不是实际输出。

扫描仪只是在源程序文本中重复查找词素,直到输入用完

Lexeme 是 input 的子串,它形成了存在于文法中的有效终结符串。每个词位都遵循一个模式,最后解释(读者可以跳过的部分)

(重要的规则是寻找最长可能的前缀形成一个有效的终端字符串,直到遇到下一个空格......解释如下)

LEXEMES :

  1. 库特
  2. <<

(虽然“<”也是有效的终端字符串,但上述规则应选择词素“<<”的模式以生成扫描仪返回的令牌)

  1. 3
  2. +
  3. 2
  4. ;

TOKENS :每次 Scanner 找到(有效)词素时,一次返回一个令牌(由 Scanner 在 Parser 请求时返回)。扫描器创建一个符号表条目如果尚未存在)(具有属性:主要是标记类别和少数其他属性),当它找到一个词位时,以生成它的标记

'#' 表示符号表条目。为了便于理解,我在上面的列表中指出了词素编号,但从技术上讲,它应该是符号表中记录的实际索引。

对于上述示例,以下标记由扫描器按指定顺序返回给解析器。

  1. <标识符,#1>

  2. <操作员,#2>

  3. <文字,#3>

  4. <操作员,#4>

  5. <文字,#5>

  6. <操作员,#4>

  7. <文字,#3>

  8. <标点符号,#6>

正如您所看到的区别,令牌是一对与词素不同,词素是输入的子字符串。

该对的第一个元素是令牌类/类别

下面列出了令牌类:

  • 关键词
  • 身份标识
  • 文字
  • 标点符号
  • 运营商
  • 还有一件事, Scanner 检测空格,忽略它们并且根本不为空格形成任何标记。并非所有分隔符都是空格,空格是扫描仪用于其目的的一种分隔符形式。输入中的制表符、换行符、空格、转义字符统称为空白分隔符。很少有其他分隔符是 ';' ',' ':' 等,它们被广泛认为是构成标记的词素。

    此处返回的令牌总数为 8,但仅为词素创建了 6 个符号表条目。词位一共有 8 个(见词位的定义)

    --- 你可以跳过这部分

    A ***pattern*** is a rule ( say, a regular expression ) that is used to check if a string-of-terminals is valid or not.

    If a substring of input composed only of grammar terminals is following the rule specified by any of the listed patterns , it is validated as a lexeme and selected pattern will identify the category of lexeme, else a lexical error is reported due to either (i) not following any of the rules or (ii) input consists of a bad terminal-character not present in grammar itself.

    for example :
    
    1. No Pattern Exists : In C++ , "99Id_Var" is grammar-supported string-of-terminals but is not recognised by any of patterns hence lexical error is reported .
    
    2. Bad Input Character : $,@,unicode characters may not be supported as a valid character in few programming languages.`
    
    Run Code Online (Sandbox Code Playgroud)