This shows you the differences between two versions of the page.
alf:teme:tema4 [2020/04/12 21:49] diana.ghindaoanu [Ce que vous devez faire] |
alf:teme:tema4 [2022/05/03 12:23] (current) diana.ghindaoanu [Information] |
||
---|---|---|---|
Line 1: | Line 1: | ||
- | ====== Devoir 4 - Semantique ====== | + | ====== Devoir 4 - Sémantique ====== |
===== Information ===== | ===== Information ===== | ||
<note important> | <note important> | ||
- | Date limite: ** le 5 mai, 23h55 ** \\ | + | Date limite: ** le 22 mai, 23h55 ** \\ |
Points: ** 2 points ** hors de la note finale \\ | Points: ** 2 points ** hors de la note finale \\ | ||
- | Téléchargez le devoir: [[https://vmchecker.cs.pub.ro|vmchecker.cs.pub.ro]] \\ | + | Téléchargez le devoir: [[https://classroom.github.com/a/P2YgEyZL | GitHub Devoir 4]] \\ |
- | Téléchargement tardif: ** 0,1 point / jour ** (maximum 4 jours) \\ | + | Téléchargement tardif: ** 1 point / jour ** (maximum 3 jours) \\ |
</note> | </note> | ||
- | ===== Ce que vous devez faire ===== | + | ===== Demande ===== |
- | Le but du devoir est d'écrire l'analyse sémantique, le langage intermédiaire pour le langage Alf. | + | L'objectif du devoir est de créer la table de symboles et d'écrire l'analyse sémantique pour le langage Alf. |
- | Vous recevrez un AST de l'analyseur qui analyse correctement une source de langue Alf et doit écrire: | + | Vous recevrez comme entrée un fichier qui contient un AST qui analyse correctement un langage source. Ce que vous devez faire est de générer: |
- | - le tableau des symboles | + | - la table des symboles |
- | - ajouter à chaque noeud d'AST un attribut // symbole // avec l'ID de contexte et déterminer les types pour les noeuds qui retournent (expr, value, id, element_of_vector,struct, function) | + | - un nouvel AST avec les modifications suivantes |
- | - la liste d'erreurs sémantiques | + | - le nouvel AST est une liste d'instructions (//statements//) |
+ | - tous les noeuds de l'AST ont une nouvelle propriété appellée **symbol**, qui fait référence a l'entrée du tableau de symboles ou ils déclarent des variables, fonctions et types | ||
+ | - le programme principal s'appelle "Statements" | ||
+ | - une liste des erreurs | ||
<note> | <note> | ||
- | Toutes les trois exigences sont vérifiées et classées séparément. Les exemples qui ne produisent pas d'erreurs recevront des points d'erreur uniquement si la table des symboles et l'AST sont corrects. | + | Toutes les trois exigences sont vérifiées et classées séparément. Les exemples qui ne produisent pas d'erreurs recevront des points d'erreur uniquement si la table de symboles et le nouvel AST sont corrects. |
</note> | </note> | ||
Line 27: | Line 30: | ||
* le fichier de sortie | * le fichier de sortie | ||
<code bash> | <code bash> | ||
- | noeud main.js source.alf source.alf.json | + | node main.js source.alf.ast.json source.alf.json |
</code> | </code> | ||
- | |||
- | ===== Le fichier de grammaire Alf ===== | ||
- | Vous pouvez utiliser votre fichier de grammaire ou le fichier [[https://github.com/alexandruradovici/alf2018/blob/master/Devoirs/alf/grammar.jison|reference]] | ||
===== Conseils pour résoudre le devoir ===== | ===== Conseils pour résoudre le devoir ===== | ||
- | * Faire le tableau des symboles | + | * Générer la table des symboles |
- | * Déterminer tous les types de variables dans le tableau des symboles | + | * Déterminer tous les types des variables dans la table des symboles |
- | * Déterminer les types pour toutes les instructions qui retournent un résultat | + | * Déterminer les types pour toutes les instructions qui retournent un résultat (expressions, fonctions) |
- | * Lors de la détermination des types, écrivez les erreurs | + | * Intégration des messages d'erreur |
===== Fichier de sortie ===== | ===== Fichier de sortie ===== | ||
Line 46: | Line 46: | ||
<code javascript> | <code javascript> | ||
{ | { | ||
- | symbol_table: [...], // le tableau symbol_table | + | symbol_table: [...], // la table de symboles |
- | ast: {...}, // l'ast avec le type pour un noeud qui retourne une valeur | + | ast: [...], // le nouvel AST |
error_list: [] // la liste des erreurs | error_list: [] // la liste des erreurs | ||
} | } | ||
</code> | </code> | ||
- | ===== Tableau des symboles ===== | + | ===== La table de symboles ===== |
- | Le tableau des symboles est un tableau d'objets de contexte. | + | La table de symboles est une liste composée par des objets représentant des **contextes**. Dans l'exemple ci-dessous, on peut voir qu'il y a 2 contextes: |
+ | * **"type": "Statements"** - le contexte du module principal, qui contient toutes les instructions | ||
+ | * **"type": "function"** - le contexte généré par la fonction _sum | ||
<code javascript> | <code javascript> | ||
- | [ | + | "symbol_table": [ |
- | // ID de l'objet de contexte 0 - le contexte du script principal | + | { |
- | { | + | "variables": {}, |
- | ... | + | "functions": { |
- | }, | + | "_sum": { |
- | // ID de l'objet de contexte 1 - l'objet de contexte d'une fonction | + | "type": "integer", |
- | { | + | "parameters": [ |
- | ... | + | { |
- | }, | + | "id": "FunctionDefinitionParameter", |
- | ... | + | "type": "integer", |
- | ] | + | "name": "n1", |
+ | "symbol": 1 | ||
+ | }, | ||
+ | { | ||
+ | "id": "FunctionDefinitionParameter", | ||
+ | "type": "integer", | ||
+ | "name": "n2", | ||
+ | "symbol": 1 | ||
+ | } | ||
+ | ], | ||
+ | "line": 4, | ||
+ | "symbol": 1 | ||
+ | } | ||
+ | }, | ||
+ | "types": {}, | ||
+ | "type": "Statements" | ||
+ | }, | ||
+ | { | ||
+ | "variables": {}, | ||
+ | "functions": {}, | ||
+ | "types": {}, | ||
+ | "parent": 0, | ||
+ | "type": "function", | ||
+ | "function": "_sum", | ||
+ | "return_type": "integer" | ||
+ | } | ||
+ | ] | ||
</code> | </code> | ||
- | Lors de la détermination de la table de symboles, ajoutez à chaque noeud AST un paramètre // symbole // avec la valeur de son identifiant de contexte. | + | Lors de la création de la table de symboles, vous devez ajouter à chaque noeud AST un paramètre //symbole//, représentant l'identifiant du contexte. |
==== Objet de contexte ==== | ==== Objet de contexte ==== | ||
- | Les objets de contexte stockent | + | Les objets de contexte stockent les suivantes propriétés: |
* la variable déclarée dans ce contexte | * la variable déclarée dans ce contexte | ||
- | * le message déclaré dans ce contexte | + | * la fonction déclarée dans ce contexte |
- | * les classes déclarées dans ce contexte | + | * les types (array, struct) déclarés dans ce contexte |
- | * l'identifiant de contexte parent (position dans le tableau symbol_table) | + | * l'identifiant du contexte parent (position dans le tableau symbol_table) |
- | * le type du contexte (module ou message) | + | * le type du contexte (Statements ou function) |
- | * le nom du message duquel est le contexte (s'il n'est pas le module) | + | * le nom de la fonction, si le contexte est de type 'function', |
- | * le nom de la classe duquel est le contexte (s'il n'est pas le module) | + | * le type de retour de la fonction |
- | * le type de la valeur de retour du message duquel est le contexte (s'il n'est pas le module) | + | * |
<note> | <note> | ||
Les objets de contexte sont générés par | Les objets de contexte sont générés par | ||
* le module principal | * le module principal | ||
- | * une définition de message | + | * une définition de fonction |
* une classe | * une classe | ||
</note> | </note> | ||
Line 94: | Line 121: | ||
<code javascript> | <code javascript> | ||
{ | { | ||
- | "variables": {// un dictionnaire des variables | + | "variables": { // a dictionary of variables |
- | "Nom de la variable": { | + | "variable_name": { |
- | "type": // type de la variable | + | "type": // type of the variable |
- | "line": // la ligne où la variable a été déclarée | + | "line": // the line where the variable was declared |
- | "value": // l'expression que la variable a initialement (facultatif, si elle a ete definie avec une valeur) | + | "value": // the expression that the variable initially has (optional, if the define was with an assignment) |
} | } | ||
}, | }, | ||
- | "messages": {// un dictionnaire des fonctions | + | "messages": { // a dictionary of functions |
"message_name": { | "message_name": { | ||
- | "type": // le type de retour de la fonction | + | "type": // the return type of the function |
- | "parametres": [] // la liste des paramètres que la fonction prenne (le noeud parameters de l'AST) | + | "parameters": [] // the list of parameters the function takes (the parameters node from the AST) |
- | "line": // la ligne où la fonction a été déclarée | + | "line": // the line where the function was declared |
- | "symbol": // l'identifiant de l'objet de contexte créé par la fonction | + | "symbol": // the context object id that the function creates |
- | | + | |
} | } | ||
- | }, | + | }, |
- | "types": {// un dictionnaire de types | + | "types": { // a dictionary of types |
"type": { | "type": { | ||
- | "type": // le type de la nouvelle classe de type ou tableau | + | "type": // the type of the new type class or array |
- | "line": // la ligne où le type a été déclaré | + | "line": // the line where the type was declared |
- | // pour le tableau | + | // for array |
- | "elements_type": // le type de chaque élément du tableau | + | "elements_type": // the type of each array element |
- | "from": // le premier index | + | "from": // the first index |
- | "to": // le dernier index | + | "to": // the last index |
- | // pour la classe | + | // for class |
- | "elements": [// une liste d'éléments de tableau (le noeud de l'AST) | + | "elements": [ // a list of array elements (the node form the AST) |
{ | { | ||
- | "type": | + | "type": |
- | "id": | + | "id": |
- | "line": | + | "line": |
}, | }, | ||
... | ... | ||
Line 129: | Line 156: | ||
} | } | ||
}, | }, | ||
- | "parent": 0, // la position du contexte parent dans le tableau symbol_table (à l'exception du script principal qui n'a pas de parent), généralement 0, | + | "parent": 0, // the parent context position in the symbol_table (except of the main script that has no parent), usually 0, |
- | "type": // | + | "type": // the type of the |
- | "message": // le nom du message s'il s'agit d'un contexte de fonction | + | "message": // the message name if this is a function context |
- | "class": // le nom de la classe si le contexte est dans un message qui est dans une classe | + | "class": // the class name if the context is in a message that is in a class |
- | "return_value": // le type de retour de la fonction s'il s'agit d'un contexte de fonction | + | "return_value": // the return type of the function if this is a function context |
} | } | ||
</code> | </code> | ||
=== Exemple === | === Exemple === | ||
+ | |||
<code javascript> | <code javascript> | ||
{ | { | ||
- | "variables": { | + | "variables": {}, |
- | "s": { | + | "functions": { |
- | "type": "school", | + | "_sum": { |
- | "line": 8 | + | "type": "integer", |
- | } | + | "parameters": [ |
- | }, | + | |
- | "messages": {}, | + | |
- | "types": { | + | |
- | "school": { | + | |
- | "type": "class", | + | |
- | "line": 6, | + | |
- | "elements": [ | + | |
{ | { | ||
- | "type": "int", | + | "id": "FunctionDefinitionParameter", |
- | "id": "type", | + | "type": "integer", |
- | "line": 5 | + | "name": "n1", |
+ | "symbol": 1 | ||
}, | }, | ||
{ | { | ||
- | "type": "logic", | + | "id": "FunctionDefinitionParameter", |
- | "id": "private", | + | "type": "integer", |
- | "line": 4 | + | "name": "n2", |
- | }, | + | "symbol": 1 |
- | { | + | |
- | "type": "string", | + | |
- | "id": "name", | + | |
- | "line": 3 | + | |
} | } | ||
- | ] | + | ], |
- | } | + | "line": 4, |
- | } | + | "symbol": 1 |
- | } | + | } |
+ | }, | ||
+ | "types": {}, | ||
+ | "type": "Statements" | ||
+ | } | ||
</code> | </code> | ||
+ | |||
===== Vérification des types dans l'AST ===== | ===== Vérification des types dans l'AST ===== | ||
- | ==== Type de retour d'expression ==== | + | ==== Type de retour des expressions ==== |
Pour chacun des noeuds suivants, déterminez le type de retour | Pour chacun des noeuds suivants, déterminez le type de retour | ||
- | * exp | + | * Expression |
- | * value | + | * Value |
- | * identifier | + | * Variable |
- | * return | + | * ReturnFunction |
- | * element | + | * ArrayElement |
- | * property | + | * ClassProperty |
- | * dispatch | + | * FunctionDefinition |
Définissez le type en ajoutant une propriété type dans le noeud. | Définissez le type en ajoutant une propriété type dans le noeud. | ||
<note> | <note> | ||
- | Lors de la recherche d'une variable, l'algorithme est: | + | L'algorithme pour chercher une variable suppose les étapes suivantes: |
- | * S'il s'agit d'un contexte de message, recherchez les variables locales | + | |
- | * Si elle n'est pas trouvé, recherchez les paramètres | + | - S'il s'agit d'un contexte de fonction, recherchez dans le contexte des variables locales |
- | * Si elle n'est pas trouvé, recherchez les variables locales du contexte de classe | + | - S'il n'a pas été trouvé, cherchez dans les parametres |
- | * si c'est le contexte du module, recherchez les variables globales | + | - S'il n'a pas été trouvé, chechez dans le contexte des variables locales des classes |
+ | - S'il s'agit du contexte du module principal, cherchez dans les variables globales | ||
</note> | </note> | ||
=== Exemple === | === Exemple === | ||
<code javascript> | <code javascript> | ||
- | { | + | { |
- | "id": "exp", | + | "id": "Expression", |
- | "op": "=", | + | "op": "+", |
- | "left": { | + | "left": { |
- | "id": "exp", | + | "id": "Value", |
- | "op": "mod", | + | "type": "integer", |
- | "left": { | + | "value": 2, |
- | "id": "id", | + | "line": 5, |
- | "value": "n", | + | "symbol": 0 |
- | "line": 8, | + | }, |
- | "symbol": 1, | + | "right": { |
- | "type": "int" | + | "id": "FunctionCall", |
- | }, | + | "function_name": "number", |
- | "right": { | + | "parameters": [], |
- | "id": "id", | + | "line": 5, |
- | "value": "i", | + | "symbol": 0, |
- | "line": 8, | + | "type": "integer" |
- | "symbol": 1, | + | }, |
- | "type": "int" | + | "line": 5, |
- | }, | + | "symbol": 0, |
- | "line": 8, | + | "type": "integer" |
- | "symbol": 1, | + | } |
- | "t": "int" | + | |
- | }, | + | |
- | "right": { | + | |
- | "id": "value", | + | |
- | "type": "int", | + | |
- | "value": 0, | + | |
- | "line": 8, | + | |
- | "symbol": 1 | + | |
- | }, | + | |
- | "line": 8, | + | |
- | "symbol": 1, | + | |
- | "type": "logic" | + | |
- | } | + | |
</code> | </code> | ||
- | ==== Vérifier les types ==== | + | ==== Vérification de la correctitude du langage ==== |
Pour tous les noeuds AST, vérifiez que les types correspondent: | Pour tous les noeuds AST, vérifiez que les types correspondent: | ||
- | * attributions sont faisables | + | * les attributions sont faisables |
* les expressions peuvent être calculées | * les expressions peuvent être calculées | ||
- | * l'expression if / while / repeat a une valeur logique | ||
* la variable est un nombre / string / boolean | * la variable est un nombre / string / boolean | ||
- | * que les variables sont définies avant d'être utilisées | + | * les variables sont définies avant d'être utilisées |
* les fonctions sont définies avant d'être utilisées | * les fonctions sont définies avant d'être utilisées | ||
- | * les index de tableau sont des nombres | + | * les indices de tableau sont des nombres |
* les propriétés de la classe existent | * les propriétés de la classe existent | ||
* la variable pour element_of_array est un tableau | * la variable pour element_of_array est un tableau | ||
Line 251: | Line 262: | ||
* les types ne sont pas redéfinis | * les types ne sont pas redéfinis | ||
- | <note> | ||
- | C'est là que la plupart des erreurs apparaissent. | ||
- | </note> | ||
===== Liste d'erreurs ===== | ===== Liste d'erreurs ===== | ||
Line 264: | Line 272: | ||
<code javascript> | <code javascript> | ||
{ | { | ||
- | type: // chaîne avec le type d'erreur | + | type: // string with the error type |
- | line: // le numéro de ligne dans la source (commençant par 1) | + | line: // the line number in the source (starting at 1) |
- | elements: // éléments pour l'erreur, chaque type d'erreur a des éléments différents | + | elements: // items for the error, each type of error has different items |
- | text: // le message d'erreur | + | text: // the error text message |
} | } | ||
</code> | </code> | ||
Line 280: | Line 288: | ||
<code javascript> | <code javascript> | ||
{ | { | ||
- | variable: // nom de la variable | + | "type": "VARIABLE_ALREADY_DEFINED", |
+ | "line": 5, | ||
+ | "elements": { | ||
+ | "variable": "var_name" | ||
+ | }, | ||
+ | "text": "variable var_name is already defined" | ||
} | } | ||
</code> | </code> | ||
Line 290: | Line 303: | ||
<code javascript> | <code javascript> | ||
{ | { | ||
- | function: // nom de la fonction | + | "type": "FUNCTION_ALREADY_DEFINED", |
+ | "line": 5, | ||
+ | "elements": { | ||
+ | "variable": "function_name" | ||
+ | }, | ||
+ | "text": "Function function_name is already defined" | ||
} | } | ||
</code> | </code> | ||
Line 300: | Line 318: | ||
<code javascript> | <code javascript> | ||
{ | { | ||
- | type: // nom du type | + | "type": "TYPE_ALREADY_DEFINED", |
- | } | + | "elements": { |
+ | "type": "s" | ||
+ | }, | ||
+ | "text": "type s is already defined" | ||
+ | } | ||
</code> | </code> | ||
- | === STRUCT_ELEMENT_ALREADY_DEFINED === | + | === CLASS_PROPERTY_ALREADY_DEFINED === |
- | L'erreur se produit lorsqu'une définition d'élément struct est répétée. | + | L'erreur se produit lorsqu'une définition d'élément class est répétée. |
== Eléments == | == Eléments == | ||
<code javascript> | <code javascript> | ||
{ | { | ||
- | struct: // nom du type de structure | + | "type": "CLASS_PROPERTY_ALREADY_DEFINED", |
- | element: // nom de l'élément | + | "line": 5, |
+ | "elements": { | ||
+ | "struct": "s" // class_name | ||
+ | }, | ||
+ | "text": "struct's class_name element title is already defined" | ||
} | } | ||
</code> | </code> | ||
Line 321: | Line 348: | ||
<code javascript> | <code javascript> | ||
{ | { | ||
- | array: // nom du type de tableau | + | "type": "ARRAY_INDEX_VALUE", |
- | low_index: // la valeur d'index inférieure | + | "line": 3, |
- | high_index: // la valeur d'index la plus élevée | + | "elements": { |
- | } | + | "array": "array_name", |
+ | "low_index": "low_index_value", | ||
+ | "high_index": "high_index_value" | ||
+ | }, | ||
+ | "text": "Array index lower value (low_index_value) must be smaller that the upper value (high_index_value)" | ||
+ | } | ||
</code> | </code> | ||
Line 336: | Line 368: | ||
variable: // le nom de la variable avec le type non résolu | variable: // le nom de la variable avec le type non résolu | ||
} | } | ||
- | // Elément struct | + | // struct property |
{ | { | ||
struct: // nom du type de structure | struct: // nom du type de structure | ||
- | element: // nom de l'élément struct avec le type non résolu | + | property: // nom de l'élément struct avec le type non résolu |
} | } | ||
</code> | </code> | ||
- | === UNDEFINED_MESSAGE === | + | === UNDEFINED_FUNCTION === |
- | L'erreur se produit lorsqu'un appel de fonction est effectué sur une fonction qui n'est pas définie. | + | L'erreur se produit lorsqu'un appel de fonction est effectué pour une fonction qui n'est pas définie. |
== Eléments == | == Eléments == | ||
<code javascript> | <code javascript> | ||
{ | { | ||
- | id: // nom du message | + | "type": "UNDEFINED_FUNCTION", |
+ | "line": 2, | ||
+ | "elements": { | ||
+ | "id": "function_name" | ||
+ | }, | ||
+ | "text": "Undefined function function_name" | ||
} | } | ||
</code> | </code> | ||
Line 360: | Line 397: | ||
<code javascript> | <code javascript> | ||
{ | { | ||
- | variable: // nom de la variable | + | "type": "UNDEFINED_VARIABLE", |
+ | "line": 3, | ||
+ | "elements": { | ||
+ | "variable": "var_name" | ||
+ | }, | ||
+ | "text": "Undefined variable var_name" | ||
} | } | ||
</code> | </code> | ||
Line 369: | Line 411: | ||
== Eléments == | == Eléments == | ||
{ | { | ||
- | variable: // la variable qui a ce type | + | "type": "UNDEFINED_TYPE", |
- | type: // le type qui n'est pas défini | + | "line": 3, |
+ | "elements": { | ||
+ | "variable": "type_name" | ||
+ | }, | ||
+ | "text": "Undefined type type_name" | ||
} | } | ||
- | === NOT_CLASS_PROPERTY === | ||
- | L'erreur se produit lorsqu'un élément ne fait pas partie de cette structure. | ||
- | == Eléments == | + | === NOT_STRUCT === |
- | <code javascript> | + | |
- | { | + | |
- | class: // nom de la structure | + | |
- | propriété: // nom de l'élément | + | |
- | } | + | |
- | </code> | + | |
- | + | ||
- | === NOT_CLASS === | + | |
L'erreur se produit lorsqu'une propriété est demandée pour une variable qui n'est pas un type de classe | L'erreur se produit lorsqu'une propriété est demandée pour une variable qui n'est pas un type de classe | ||
Line 390: | Line 426: | ||
<code javascript> | <code javascript> | ||
{ | { | ||
- | type: // type réel que la variable est (au lieu d'un type struct) | + | "type": "NOT_STRUCT", |
+ | "line": 13, | ||
+ | "elements": { | ||
+ | "type": "var_name" | ||
+ | }, | ||
+ | "text": "var_name is not a struct" | ||
} | } | ||
+ | |||
</code> | </code> | ||
Line 400: | Line 442: | ||
<code javascript> | <code javascript> | ||
{ | { | ||
- | type: // type réel que la variable est (au lieu d'un type de tableau) | + | "type": "NOT_ARRAY", |
+ | "line": 5, | ||
+ | "elements": { | ||
+ | "type": "var_name" | ||
+ | }, | ||
+ | "text": "var_name is not an array" | ||
} | } | ||
</code> | </code> | ||
Line 410: | Line 457: | ||
<code javascript> | <code javascript> | ||
{ | { | ||
- | array: // type de tableau | + | "type": "ARRAY_INDEX_TYPE", |
- | index: // type d'index fourni | + | "line": 7, |
- | } | + | "elements": { |
+ | "array": "array_name", | ||
+ | "index": "string" | ||
+ | }, | ||
+ | "text": "Array (array_name) index must be integer or symbol" | ||
+ | } | ||
</code> | </code> | ||
- | === RETURN_OUTSIDE_MESSAGE === | + | === RETURN_OUTSIDE_FUNCTION === |
L'erreur se produit lorsqu'une instruction de valeur (noeud de retour) est utilisée en dehors d'un message | L'erreur se produit lorsqu'une instruction de valeur (noeud de retour) est utilisée en dehors d'un message | ||
Line 421: | Line 473: | ||
<code javascript> | <code javascript> | ||
{ | { | ||
- | // vide | + | "type": "RETURN_OUTSIDE_FUNCTION", |
+ | "line": 3, | ||
+ | "elements": {}, | ||
+ | "text": "value is used out of function" | ||
} | } | ||
</code> | </code> | ||
Line 430: | Line 485: | ||
== Eléments == | == Eléments == | ||
<code javascript> | <code javascript> | ||
- | // left op right | ||
{ | { | ||
- | left: | + | "type": "TYPE_EXPRESSION", |
- | right: | + | "line": 6, |
- | op: | + | "elements": { |
- | } | + | "op": "=", |
- | // op value | + | "to": "to_type", |
- | { | + | "from": "from_type" |
- | value: | + | }, |
- | op: | + | "text": "Type expression error to_type is from_type" |
- | } | + | |
- | // if, while or repeat | + | |
- | { | + | |
- | expression: // expression type | + | |
- | op: // if, while, repeat | + | |
- | } | + | |
- | // for | + | |
- | { | + | |
- | expression: // expression type | + | |
- | op: "for" | + | |
- | element: | + | |
- | } | + | |
- | // value_of_function | + | |
- | { | + | |
- | op: "value" | + | |
- | to: // return type | + | |
- | from: // provided type | + | |
- | } | + | |
- | // assign | + | |
- | { | + | |
- | op: ":=" | + | |
- | to: // to type | + | |
- | from: // from type | + | |
- | } | + | |
- | // struct element type is undefined | + | |
- | { | + | |
- | struct: // struct type, | + | |
- | element: // name of struct element | + | |
- | } | + | |
- | // variable type is undefined | + | |
- | { | + | |
- | variable: // name of the variable | + | |
} | } | ||
</code> | </code> | ||
- | |||
- | === LEXICAL === | ||
- | Ceci est une erreur lexicale. | ||
- | |||
- | == Eléments == | ||
- | <code javascript> | ||
- | { | ||
- | line: // le numéro de ligne | ||
- | text: // le texte de l'erreur | ||
- | } | ||
- | </ code> | ||
- | |||
- | === SYNTAXE === | ||
- | Ceci est une erreur de syntaxe | ||
- | |||
- | == Eléments == | ||
- | <code javascript> | ||
- | { | ||
- | line: // le numéro de ligne | ||
- | text: // le texte de l'erreur | ||
- | token: // le jeton obtenu | ||
- | expected: [] / la liste des jetons attendus | ||
- | } | ||
- | </code> | ||
- | |||
===== Bonus ===== | ===== Bonus ===== | ||
Line 523: | Line 520: | ||
Si vous souhaitez recevoir un e-mail lorsque des problèmes sont signalés ou lorsqu'il y a de nouveaux messages, accédez au site github [[https://github.com/alexandruradovici/alf2018|repository]] et cliquez sur // Watch //. | Si vous souhaitez recevoir un e-mail lorsque des problèmes sont signalés ou lorsqu'il y a de nouveaux messages, accédez au site github [[https://github.com/alexandruradovici/alf2018|repository]] et cliquez sur // Watch //. | ||
- | ===== Tests ===== | ||
- | Les devoirs seront testés automatiquement en utilisant un ensemble de tests publics et privés. | ||
- | |||
- | ==== Tests publics ==== | ||
- | |||
- | Vous pouvez télécharger les tests publics de GitHub [[https://github.com/alexandruradovici/alf2018.git|repository]]. | ||
- | |||
- | Pour exécuter les tests, téléchargez le contenu du référentiel dans le directoire avec les devoirs. Entrez dans le directoire // verify // et exécutez ./run_all.sh. | ||
- | |||
- | <code bash> | ||
- | cd verify | ||
- | ./run_all.sh | ||
- | </code> | ||
- | |||
- | Vous aurez besoin de bash pour ça. Vous pouvez utiliser Linux ou [[https://msdn.microsoft.com/fr-fr/commandline/wsl/install_guide|Windows Linux Subsystem]]. | ||
- | |||
- | <note> | ||
- | Pour installer nodejs sous Linux ou Windows Linux Subsystem, procédez comme suit: | ||
- | |||
- | <code bash> | ||
- | wget https://nodejs.org/dist/v8.9.4/node-v8.9.4-linux-x64.tar.xz | ||
- | tar xvfJ node-v8.9.4-linux-x64.tar.xz | ||
- | cd node-v8.9.4-linux-x64 | ||
- | sudo cp -R * /usr | ||
- | </code> | ||
- | |||
- | </note> | ||
- | |||
- | ==== Tests privés ==== | ||
- | Lors du téléchargement des devoirs, il est possible qu'on a des tests privés à faire passer. vmchecker les exécutera. | ||
- | |||
- | <note> | ||
- | Vous pouvez toujours télécharger les devoirs autant de fois que vous le souhaitez jusqu'à la date limite. Cela va exécuter tous les tests pour vous et afficher le résultat. | ||
- | </note> | ||
- | |||
- | ===== Télécharger les devoirs ===== | ||
- | Le devoir doit être téléchargé sur [[https://vmchecker.cs.pub.ro | vmchecker]]. Connectez-vous avec votre nom d'utilisateur moodle, sélectionnez le //cours Automates et Langages Formelles (FILS)// et téléchargez [[# homework-archive | homework archive]]. | ||
- | |||
- | ==== Readme ==== | ||
- | Le fichier readme a le format suivant: | ||
- | |||
- | <code> | ||
- | Nom complet | ||
- | Groupe | ||
- | |||
- | Une explication comment vous avez écrit vos devoirs, qu'avez vous utilisé, quelles sont les idées principales. | ||
- | </code> | ||
- | |||
- | |||
- | ==== Archive des devoirs ==== | ||
- | Pour télécharger vos devoirs, suivez les instructions suivantes: | ||
- | |||
- | - Créer une archive zip (pas rar, ace, 7zip ou autre) conten | ||
- | * votre fichier principal | ||
- | * votre fichier grammar.jison | ||
- | * vos fichiers javascript (*.js) | ||
- | * le fichier package.json | ||
- | * le fichier Readme | ||
- | - Connectez-vous avec [[https://vmchecker.cs.pub.ro | vmchecker]] | ||
- | - sélectionner les //Automates et Langages Formelles (FILS)// cours | ||
- | - sélectionnez //4. Sémantique// | ||
- | - télécharger l'archive | ||
- | |||
- | |||
- | <note> | ||
- | L'archive doit contenir les fichiers dans sa racine, pas dans un directoire. NE PAS archiver un dossier avec des fichiers, archiver DIRECTEMENT les fichiers. | ||
- | |||
- | NE PAS inclure // node_modules //. | ||
- | </note> | ||
- | |||
- | Lorsque l'archive est téléchargée, vmchecker va exécuter: | ||
- | |||
- | <code bash> | ||
- | unzip archive.zip homework | ||
- | cd homework | ||
- | npm install | ||
- | echo '{ "node":true, "esnext":true }' > .jshintrc | ||
- | jshint *.js | ||
- | </code> |