diff --git a/Module2/SimpleLangLexer/SimpleLexer.cs b/Module2/SimpleLangLexer/SimpleLexer.cs index 7bd0af4e65a57a95a208e01d8242bf4f0d50d410..73630fd6309bd1c25d7020df4d6f9de02229b0d2 100644 --- a/Module2/SimpleLangLexer/SimpleLexer.cs +++ b/Module2/SimpleLangLexer/SimpleLexer.cs @@ -1,4 +1,4 @@ -using System; +using System; using System.Collections; using System.Collections.Generic; using System.IO; @@ -19,19 +19,19 @@ namespace SimpleLexer { EOF, ID, - INUM, - COLON, - SEMICOLON, - ASSIGN, - BEGIN, - END, - CYCLE, - COMMA, + INUM, // num + COLON, // : + SEMICOLON, // ; + ASSIGN, // = + BEGIN, // { + END, // } + CYCLE, // while + COMMA, // , PLUS, MINUS, MULT, DIVISION, - MOD, + MOD, // % DIV, AND, OR, @@ -53,11 +53,11 @@ namespace SimpleLexer IF, THEN, ELSE, - LEFT_BRACKET, - RIGHT_BRACKET, + LEFT_BRACKET, // ( + RIGHT_BRACKET, // ) } - public class Lexer + public class Lexer { private int position; private char currentCh; // Текущий символ @@ -70,7 +70,7 @@ namespace SimpleLexer public int LexValue; // Целое значение, связанное с лексемой LexNum private string CurrentLineText; // Накапливает символы текущей строки для сообщений об ошибках - + public Lexer(TextReader input) { @@ -83,7 +83,8 @@ namespace SimpleLexer NextLexem(); // Считать первую лексему, заполнив LexText, LexKind и, возможно, LexValue } - public void Init() { + public void Init() + { } @@ -100,6 +101,43 @@ namespace SimpleLexer keywordsMap["begin"] = Tok.BEGIN; keywordsMap["end"] = Tok.END; keywordsMap["cycle"] = Tok.CYCLE; + keywordsMap["while"] = Tok.WHILE; + keywordsMap["do"] = Tok.DO; + keywordsMap["for"] = Tok.FOR; + keywordsMap["to"] = Tok.TO; + keywordsMap["if"] = Tok.IF; + keywordsMap["else"] = Tok.ELSE; + keywordsMap["then"] = Tok.THEN; + keywordsMap["("] = Tok.LEFT_BRACKET; + keywordsMap[")"] = Tok.RIGHT_BRACKET; + + keywordsMap["+"] = Tok.PLUS; + keywordsMap["-"] = Tok.MINUS; + keywordsMap["*"] = Tok.MULT; + keywordsMap["/"] = Tok.DIVASSIGN; + keywordsMap["+="] = Tok.PLUSASSIGN; + keywordsMap["-="] = Tok.MINUSASSIGN; + keywordsMap["*="] = Tok.MULTASSIGN; + keywordsMap["/="] = Tok.DIVASSIGN; + + keywordsMap["div"] = Tok.DIV; + keywordsMap["mod"] = Tok.MOD; + keywordsMap["and"] = Tok.AND; + keywordsMap["or"] = Tok.OR; + keywordsMap["not"] = Tok.NOT; + + keywordsMap["="] = Tok.EQ; + keywordsMap[">="] = Tok.GEQ; + keywordsMap["<="] = Tok.LEQ; + keywordsMap[">"] = Tok.GT; + keywordsMap["<"] = Tok.LT; + keywordsMap["<>"] = Tok.NEQ; + + keywordsMap[";"] = Tok.SEMICOLON; + keywordsMap[","] = Tok.COMMA; + keywordsMap[":"] = Tok.COLON; + keywordsMap[":="] = Tok.ASSIGN; + } public string FinishCurrentLine() @@ -163,16 +201,192 @@ namespace SimpleLexer NextCh(); LexKind = Tok.SEMICOLON; } + else if (currentCh == ',') + { + NextCh(); + LexKind = Tok.COMMA; + } else if (currentCh == ':') { NextCh(); - if (currentCh != '=') + if (currentCh == '=') + { + LexKind = Tok.ASSIGN; + NextCh(); + } + else + { + LexKind = Tok.COLON; + } + } + + + + + + + + else if (currentCh == '+') + { + NextCh(); + if (currentCh == '=') + { + NextCh(); + LexKind = Tok.PLUSASSIGN; + } + else + { + LexKind = Tok.PLUS; + } + } + + else if (currentCh == '-') + { + NextCh(); + if (currentCh == '=') + { + NextCh(); + LexKind = Tok.MINUSASSIGN; + } + else + { + LexKind = Tok.MINUS; + } + } + + else if (currentCh == '*') + { + NextCh(); + if (currentCh == '=') + { + NextCh(); + LexKind = Tok.MULTASSIGN; + } + else + { + LexKind = Tok.MULT; + } + } + + else if (currentCh == '/') + { + NextCh(); + if (currentCh == '=') + { + NextCh(); + LexKind = Tok.DIVASSIGN; + } + else if (currentCh == '/') + { + while (true) + { + if ((int)currentCh == 0) + { + LexKind = Tok.EOF; + break; + } + else if (currentCh == '\r') + { + NextCh(); + NextLexem(); + break; + } + NextCh(); + } + + + } + else + { + LexKind = Tok.DIVISION; + } + } + + + else if (currentCh == '{') + { + NextCh(); + while (true) { - LexError("= was expected"); + if (currentCh == '}') + { + NextCh(); + NextLexem(); + break; + } + else if ((int)currentCh == 0) + { + LexError("} was expected"); + } + NextCh(); } + } + + + + //= + else if (currentCh == '=') + { NextCh(); - LexKind = Tok.ASSIGN; + LexKind = Tok.EQ; } + + //> + else if (currentCh == '>') + { + NextCh(); + if (currentCh == '=') + { + NextCh(); + LexKind = Tok.GEQ; + } + else + { + LexKind = Tok.GT; + } + } + + //< + else if (currentCh == '<') + { + NextCh(); + if (currentCh == '=') + { + NextCh(); + LexKind = Tok.LEQ; + } + else if (currentCh == '>') + { + NextCh(); + LexKind = Tok.NEQ; + } + else + { + LexKind = Tok.LT; + } + } + + + + else if (currentCh == '(') + { + NextCh(); + LexKind = Tok.LEFT_BRACKET; + } + + else if (currentCh == ')') + { + NextCh(); + LexKind = Tok.RIGHT_BRACKET; + } + + + + + + + + else if (char.IsLetter(currentCh)) { while (char.IsLetterOrDigit(currentCh)) @@ -221,9 +435,11 @@ namespace SimpleLexer var result = t.ToString(); switch (t) { - case Tok.ID: result += ' ' + LexText; + case Tok.ID: + result += ' ' + LexText; break; - case Tok.INUM: result += ' ' + LexValue.ToString(); + case Tok.INUM: + result += ' ' + LexValue.ToString(); break; } return result; diff --git a/TestSimpleLexer/Tests.cs b/TestSimpleLexer/Tests.cs index 14165974a952d77ad4d72a746988f0904d4bc9e2..3a9b7547be887e32e02f073ba86bc674f64ce46e 100644 --- a/TestSimpleLexer/Tests.cs +++ b/TestSimpleLexer/Tests.cs @@ -19,7 +19,7 @@ namespace TestSimpleLexer } [TestFixture] - [Ignore("This test is disabled")] + // [Ignore("This test is disabled")] public class TestSimpleLexer { public static List< KeyValuePair<Tok, string> > getLexerOutput(Lexer l) @@ -56,7 +56,7 @@ namespace TestSimpleLexer } [TestFixture] - [Ignore("This test is disabled")] + //[Ignore("This test is disabled")] public class TestSimpleLexerOps { [Test] @@ -126,7 +126,7 @@ namespace TestSimpleLexer } [TestFixture] - [Ignore("This test is disabled")] + //[Ignore("This test is disabled")] public class TestSimpleLexerAssigns { [Test] @@ -164,7 +164,7 @@ namespace TestSimpleLexer public class TestSimpleLexerComparisons { [Test] - [Ignore("This test is disabled")] + // [Ignore("This test is disabled")] public void TestComparisons() { string text = @"><>>=<=+<> > <="; @@ -218,7 +218,7 @@ namespace TestSimpleLexer } [TestFixture] - [Ignore("This test is disabled")] + //[Ignore("This test is disabled")] public class TestSimpleLexerLineCmt { [Test] @@ -280,7 +280,7 @@ namespace TestSimpleLexer } [TestFixture] - [Ignore("This test is disabled")] + // [Ignore("This test is disabled")] public class TestSimpleLexerMultLineCmt { [Test]