大多数C / C ++编译器如何为数组创建令牌?

时间:2018-04-21 16:39:59

标签: compiler-errors compiler-construction compiler-warnings

所以我想我有两个与大多数c / c ++编译器相关的问题:

1。  当大多数c / c ++编译器的扫描器看到像MyArray [20]这样的东西时,它创建的标记是什么?大多数编译器是否会创建一个像 array_token array_token [const_int] 或......的标记? (我想知道将数据转换为令牌后数据大小会发生什么变化) 这个问题与我的第二个问题有点相关

2。  当我们在代码中间(而不是在声明中)编写类似MyArray [20.5]的东西时,解析器是否使用语法检测到这个错误,或者我们只能使用语义例程来检测它?

重要提示 :我说的是大多数c / c ++编译器和最常用的方式,我知道一些罕见的编译器可能会采用不同的方式,但是如何做大多数编译器都采取行动?什么是常态?或者至少最受欢迎的编译器如何工作? (在我们的考试中,他们只是说它是一个c / c ++编译器,所以我们必须假设它像大多数编译器一样)

我对第二个问题的看法:

我认为解析器无法检测到这一点,因为我们可以在范围内有一个表达式,如MyArray [I * j]因此我们有类似S - >的东西。我们的语法中的array_token [expression],因为表达式中可以有float,所以解析器不会检测到错误 但如果我错了,请纠正我。

1 个答案:

答案 0 :(得分:0)

  1. 根据ISO C标准中描述的词汇规则,MyArray[20]是标识符,后跟[,后跟整数常量,后跟] 。我希望大多数(甚至所有)C编译器能够完全像这样表示它。在标准或我所知道的任何实现中都没有定义数组令牌。

  2. 数组下标的语法规则是:

    postfix-expression:  postfix-expression [ expression ]
    

    MyArray[20.5]符合该规则,因此它在语法上有效。它是类型错误,而不是语法错误。因此,检测该错误是语义分析器的工作。

  3. (回应您的评论)

      

    如果我们有像INT数组[10.5]这样的东西,它会变成这个-------> int id [const_token]因此解析器会检测到这个正确吗? (这次我在宣言中谈到),因为我们可以在语法中有一个规则,如S - > ID [int_const]

    数组声明符的C89 1 语法规则(声明中int之后的部分)如下:

     direct-declarator: direct-declarator [ constant-expressionopt ]

    array[10.5]匹配该规则(因为direct-declarator: identifier是另一个规则),因此int array[10.5]是语法上有效的声明。同样,它是一个语义错误,而不是语法错误。

    PS:请注意,constant-expression只是被定义为conditional-expression的别名。表达式实际上应该是常量的这一事实不是由语法强制执行的,也是一种语义属性。

  4. 1 我使用了C89中的规则,因为它比以后的版本更简单。但是,后来的版本在与问题相关的方式上没有区别。