2012-04-04 12 views
2

Ich schreibe einen PLC-Spracheninterpreter mit C#. Mein Interpreter hat seine eigene Typhierarchie: elementare Typen (Ganzzahlen, Boolesche, ..) und abgeleitete Typen (Strukturen, Arrays, ...). Ich habe Probleme beim Erstellen mehrdimensionaler Arrays aus meiner ANTLR-Grammatik.Erstellen multidimensionaler Arrays aus ANTLR-Grammatik

Dies ist die Art und Weise meine Sprache multidimensionalen Arrays (3x2 int-Array) erklärt:

TYPE 
    MY_ARRAY : ARRAY [0..2, 1..2] OF INT; 
END_TYPE 

Meine antlr Grammatik eindimensional Array Erklärungen für das Parsen nächsten ist:

decl_derivated 
    : 'TYPE' NEWLINE* ID ':' NEWLINE* type_decl ';' NEWLINE* 'END_TYPE' NEWLINE* -> ^(TYPEDEF<TypeDefinition>[$ID.text, $type_decl.type]) 
    ; 

type_decl returns [Type type] 
    : 'STRUCT' NEWLINE* decl_fields 'END_STRUCT' { $type = new STRUCT($decl_fields.fieldList); } 
    | 'ARRAY' '[' range ']' 'OF' type_var { $type = new ARRAY($type_var.type, $range.init, $range.end); } 
    ; 

range returns [int init, int end] 
    : ini=CTE_INT '..' en=CTE_INT { $init = int.Parse($ini.text); $end = int.Parse($en.text); } 
    ; 

type_var returns [Type type] 
    : 'BOOL' { $type = new BOOL(); } 
    | 'INT' { $type = new INT(); } 
    | 'REAL' { $type = new REAL(); } 
    ; 

/* lexer */ 

ID : (LETTER | '_') (LETTER | DIGIT | '_')* 
    ; 

fragment 
DIGIT : '0'..'9' 
     ; 

fragment 
INTEGER : DIGIT ('_'|DIGIT)* 
    ; 

fragment 
EXPONENT : ('e'|'E') ('+'|'-')? INTEGER ; 

fragment 
CTE_INT 
    : ('+'|'-'|) INTEGER 
    ; 

fragment 
CTE_REAL 
    : ('+'|'-'| /*vacio*/) INTEGER '.' INTEGER EXPONENT? 
    ; 

RANGE : '..' ; 

RANGE_OR_INT 
    : (CTE_INT RANGE) => CTE_INT { $type=CTE_INT; } 
     | (CTE_REAL) => CTE_REAL  { $type=CTE_REAL; } 
     | CTE_INT     { $type=CTE_INT; } 
    ; 

NEWLINE : '\r'? '\n' 
    | '\r' 
    ; 

ich keine Probleme zu Parser mehrdimensionale Arrays meine Grammatik in Array-Deklaration an wechselnde:

type_decl returns [Type type] 
     : 'ARRAY' '[' range (',' range)* ']' 'OF' type_var 

Ich weiß nicht, wie ich meinen Konstruktor für diese mehrdimensionalen Arrays schreiben soll. Kann mir jemand helfen? Danke.

+0

'decl_array [Liste listaInit, List listaFin] returns [Typ Typ] \t:‚ARRAY '' ['r1 = Bereich {$ listaInit.Add ($ r1.init); $ listaFin.Add ($ r1.end); } \t (',' r2 = Bereich {$ listaInit.Add ($ r2.init); $ listaFin.Add ($ r2.end);}) * ']' 'OF' type_var \t {$ type = neu ARRAY ($ type_var.type, $ listaInit, $ listaFin); } \t \t; 'So habe ich versucht, es zu lösen. Innerhalb des Array-Konstruktors erstelle ich das mehrdimensionale Array, aber ich denke, es muss ein besserer Weg dafür gewesen sein. –

+0

Können Sie das in Ihre Frage ändern? Es wäre viel einfacher zu lesen. Vielen Dank! (Ich habe versucht, aber .. die Zeilenumbrüche richtig zu bekommen ist mehr Arbeit, als ich um 3:00 Uhr gut machen kann :) – sarnold

+0

Vielen Dank für Ihre Zeit;) –

Antwort

1

SOLUTION

Schließlich habe ich eine bessere und elegantere Lösung erreicht. Ich habe meiner ARRAY-Datentypklasse zwei neue Methoden hinzugefügt: eine zum Hinzufügen einer neuen Dimension und eine weitere zum Festlegen des Basistyps.

public class ARRAY : ANY_DERIVED 
    { 
     public Type de; // ARRAY type 
     public int size; 
     public int initIndex; 
     public int finalIndex; 

    public ARRAY(int initIndex, int finalIndex) 
    { 
     this.initIndex = initIndex; 
     this.finalIndex = finalIndex; 
     size = finalIndex - initIndex + 1; 
    } 

    public void NewDim(int initIndex, int finalIndex) 
    { 
     if (de == null) 
      de = new ARRAY(initIndex, finalIndex); 
     else 
      ((ARRAY)de).NewDim(initIndex, finalIndex); 
    } 

    public void SetBaseType(Type t) 
    { 
     if (de == null) 
      de = t; 
     else 
      ((ARRAY)de).SetBaseType(t); 
    } 
    } 

ANTLR Grammatik:

decl_type returns [Type type] 
    : 'ARRAY' '[' r1=range {$type = new ARRAY($r1.init, $r1.end);} (',' r2=range {((ARRAY)$type).NewDim($r2.init, $r2.end);})* ']' 'OF' type_var { ((ARRAY)$type).SetBaseType($type_var.type); }  
    ; 

Wie dem auch sei, wir danken Ihnen für Ihre Zeit;)

Verwandte Themen