Je suppose que vous utilisez this grammar.
Bien que cette grammaire suggère qu'une AST appropriée est créée, ce n'est pas le cas. Il utilise certains opérateurs en ligne pour exclure certains jetons de l'arbre d'analyse, mais il ne crée jamais de racines pour l'arbre, ce qui donne un arbre d'analyse complètement plat. De cela, vous ne pouvez pas obtenir toutes les vars globales d'une manière raisonnable.
Vous devrez ajuster la grammaire légèrement:
Ajoutez les lignes suivantes sous la options { ... }
en haut du fichier de grammaire:
tokens
{
VARIABLE;
FUNCTION;
}
remplacent maintenant les règles suivantes: functionDeclaration
, functionExpression
et variableDeclaration
avec ceux-ci:
functionDeclaration
: 'function' LT* Identifier LT* formalParameterList LT* functionBody
-> ^(FUNCTION Identifier formalParameterList functionBody)
;
functionExpression
: 'function' LT* Identifier? LT* formalParameterList LT* functionBody
-> ^(FUNCTION Identifier? formalParameterList functionBody)
;
variableDeclaration
: Identifier LT* initialiser?
-> ^(VARIABLE Identifier initialiser?)
;
Maintenant, un arbre plus approprié est généré. Si vous analysez maintenant la source:
var a = 1; function foo() { var b = 2; } var c = 3;
l'arbre suivant est généré:

Tout ce que vous avez maintenant à faire est itérer sur les enfants de la racine de votre arbre et quand vous trébuchez sur un jeton VARIABLE
, vous savez que c'est un "global" puisque toutes les autres variables seront sous FUNCTION
nœuds.
est ici comment faire:
import org.antlr.runtime.*;
import org.antlr.runtime.tree.*;
public class Main {
public static void main(String[] args) throws Exception {
String source = "var a = 1; function foo() { var b = 2; } var c = 3;";
ANTLRStringStream in = new ANTLRStringStream(source);
JavaScriptLexer lexer = new JavaScriptLexer(in);
CommonTokenStream tokens = new CommonTokenStream(lexer);
JavaScriptParser parser = new JavaScriptParser(tokens);
JavaScriptParser.program_return returnValue = parser.program();
CommonTree tree = (CommonTree)returnValue.getTree();
for(Object o : tree.getChildren()) {
CommonTree child = (CommonTree)o;
if(child.getType() == JavaScriptParser.VARIABLE) {
System.out.println("Found a global var: "+child.getChild(0));
}
}
}
}
qui produit la sortie suivante:
Found a global var: a
Found a global var: c
+1 et une réponse. Merci beaucoup pour la réponse complète. –
@Christopher, de rien. –