From 65c7618c2a8834616b009195f10c6cd762f43b8a Mon Sep 17 00:00:00 2001 From: Mincho Paskalev Date: Wed, 7 Nov 2018 10:31:59 +0200 Subject: Добавяне на второ домашно (#30) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * Add 1st hw * --amend * moving readme for 1st hw to designated folder * renamed TokenType enum to TokenClass * fixed character constant lexing. added sampe output file * add new line at end-of-file. added gitignore * a bit of refactoring * adding cyclomatic complexity * refactored * adding cyclomatic complexity * refactored --- homework/81568/c2html/lexcer.cpp | 178 ++++++++++----------------------------- 1 file changed, 46 insertions(+), 132 deletions(-) (limited to 'homework/81568/c2html/lexcer.cpp') diff --git a/homework/81568/c2html/lexcer.cpp b/homework/81568/c2html/lexcer.cpp index 6ad3dbd..df28e6f 100644 --- a/homework/81568/c2html/lexcer.cpp +++ b/homework/81568/c2html/lexcer.cpp @@ -4,30 +4,22 @@ #include #include -// using LexCer::TokenClass; -// using LexCer::Token; -// using LexCer::keywords; -// using LexCer::preprocessor; -// using LexCer::tokenToClass; -// using LexCer::spanBegin; -// using LexCer::spanEnd; - -//const char* Tokenizer::spanBegin = "").append(lexeme).append(spanEnd); - - if (fputs(output.c_str(), out) == EOF) { - printf("Error while writing to output"); - return false; - } - return true; -} - -std::string Tokenizer::escapeHTML(const std::string &lexeme) { - std::string result; - for (auto c : lexeme) { - switch(c) { - case '<': - result.append("<"); - break; - case '>': - result.append(">"); - break; - case '&': - result.append("&"); - break; - default: - result.push_back(c); - break; - } - } - return result; -} - -TokenClass Tokenizer::nextToken(std::string *lexeme, double *number) { +Token Tokenizer::nextToken(std::string *lexeme, double *number) { + TokenClass type; if (token.type == TokenClass::Eof) { - return TokenClass::Invalid; + return makeToken(TokenClass::Invalid, *lexeme, *number); } char c = fgetc(in); if (c == EOF) { - return TokenClass::Eof; + return makeToken(TokenClass::Eof, *lexeme, *number); } lexeme->push_back(c); // operator || symbol || string || preprocessor directive @@ -251,22 +190,24 @@ TokenClass Tokenizer::nextToken(std::string *lexeme, double *number) { case ' ': case ';': case ',': - case '{': - case '}': - return TokenClass::Skip; + return makeToken(TokenClass::Skip, *lexeme, *number); case '(': - return TokenClass::LeftParen; + return makeToken(TokenClass::LeftParen, *lexeme, *number); case ')': - return TokenClass::RightParen; + return makeToken(TokenClass::RightParen, *lexeme, *number); + case '{': + return makeToken(TokenClass::LeftCurly, *lexeme, *number); + case '}': + return makeToken(TokenClass::RightCurly, *lexeme, *number); case '[': case ']': case '?': case ':': - return TokenClass::Operator; + return makeToken(TokenClass::Operator, *lexeme, *number); case '*': c = fgetc(in); if (c == '/') { - return TokenClass::Invalid; + return makeToken(TokenClass::Invalid, *lexeme, *number); } ungetc((unsigned) c, in); c = '*'; @@ -278,7 +219,7 @@ TokenClass Tokenizer::nextToken(std::string *lexeme, double *number) { c = fgetc(in); if (c != '=') ungetc((unsigned) c, in); else lexeme->push_back(c); - return TokenClass::Operator; + return makeToken(TokenClass::Operator, *lexeme, *number); case '<': case '>': c = fgetc(in); @@ -292,11 +233,11 @@ TokenClass Tokenizer::nextToken(std::string *lexeme, double *number) { } else if (lexeme->at(lexeme->size() - 1) == '<' && isalpha(c)) { lexeme->push_back(c); if (!readInclude(lexeme)) - return TokenClass::Invalid; - return TokenClass::String; + return makeToken(TokenClass::Invalid, *lexeme, *number); + return makeToken(TokenClass::String, *lexeme, *number); } else ungetc((unsigned) c, in); - return TokenClass::Operator; + return makeToken(TokenClass::Operator, *lexeme, *number); case '&': case '|': case '+': @@ -305,18 +246,18 @@ TokenClass Tokenizer::nextToken(std::string *lexeme, double *number) { lexeme->push_back(c); else ungetc((unsigned) c, in); - return TokenClass::Operator; + return makeToken(TokenClass::Operator, *lexeme, *number); case '-': c = fgetc(in); if (c == '-' || c == '=' || c == '>') lexeme->push_back(c); else ungetc((unsigned) c, in); - return TokenClass::Operator; + return makeToken(TokenClass::Operator, *lexeme, *number); case '#': if (readNextDirective(lexeme)) - return TokenClass::PreprocessorDirective; - return TokenClass::Invalid; + return makeToken(TokenClass::PreprocessorDirective, *lexeme, *number); + return makeToken(TokenClass::Invalid, *lexeme, *number); case '\'': lexeme->push_back(c = fgetc(in)); if (c == '\\') { @@ -324,90 +265,63 @@ TokenClass Tokenizer::nextToken(std::string *lexeme, double *number) { } lexeme->push_back(c = fgetc(in)); // the closing mark if (c != '\'') - return TokenClass::Invalid; - return TokenClass::String; + return makeToken(TokenClass::Invalid, *lexeme, *number); + return makeToken(TokenClass::String, *lexeme, *number); case '"': if (readNextString(lexeme, c)) - return TokenClass::String; - return TokenClass::Invalid; + return makeToken(TokenClass::String, *lexeme, *number); + return makeToken(TokenClass::Invalid, *lexeme, *number); case '/': c = fgetc(in); lexeme->push_back(c); switch (c) { case '=': - return TokenClass::Operator; + return makeToken(TokenClass::Operator, *lexeme, *number); case '/': if (!readLineComment(lexeme)) - return TokenClass::Invalid; - return TokenClass::Comment; + return makeToken(TokenClass::Invalid, *lexeme, *number); + return makeToken(TokenClass::Comment, *lexeme, *number); case '*': if (!readMultilineComment(lexeme)) - return TokenClass::Invalid; - return TokenClass::Comment; + return makeToken(TokenClass::Invalid, *lexeme, *number); + return makeToken(TokenClass::Comment, *lexeme, *number); default: if (!isblank(c) || !isdigit(c)) { ungetc((unsigned) c, in); lexeme->pop_back(); - return TokenClass::Invalid; + return makeToken(TokenClass::Invalid, *lexeme, *number); } - return TokenClass::Operator; + return makeToken(TokenClass::Operator, *lexeme, *number); } case '\\': c = fgetc(in); ungetc((unsigned) c, in); if (c != '\n') - return TokenClass::Invalid; // stray '\' - return TokenClass::Operator; + return makeToken(TokenClass::Invalid, *lexeme, *number); // stray '\' + return makeToken(TokenClass::Operator, *lexeme, *number); } // identifier || keyword || typename if (isalpha(c) || c == '_') { if (readNextIdentifier(lexeme)) { if (keywords.count(*lexeme) != 0) - return TokenClass::Keyword; + return makeToken(TokenClass::Keyword, *lexeme, *number); else if (typenames.count(*lexeme) != 0) - return TokenClass::Typename; - return TokenClass::Identifier; + return makeToken(TokenClass::Typename, *lexeme, *number); + return makeToken(TokenClass::Identifier, *lexeme, *number); } else { - return TokenClass::Invalid; + return makeToken(TokenClass::Invalid, *lexeme, *number); } } if (!isdigit(c)) { - return TokenClass::Invalid; + return makeToken(TokenClass::Invalid, *lexeme, *number); } // number if (readNextNumber(c, number, lexeme)) - return TokenClass::Number; - return TokenClass::Invalid; + return makeToken(TokenClass::Number, *lexeme, *number); + return makeToken(TokenClass::Invalid, *lexeme, *number); } - - -std::string getOutputFileName(const std::string &name) { - auto pos = name.find_last_of('.'); - if (pos == std::string::npos) { - return name + ".html"; - } - return name.substr(0, pos) + ".html"; -} - -void lexCit(FILE *in, FILE *out) { - Tokenizer hl {in, out}; - - std::string lexeme; - double number; - TokenClass type; - do { - type = hl.nextToken(&lexeme, &number); - - hl.makeToken(type, hl.lineNumber(), lexeme, number); - if (!hl.writeToOutput()) - break; - lexeme = ""; - number = 0.0; - } while(hl.currentToken().type != TokenClass::Eof || hl.currentToken().type != TokenClass::Invalid); -} - } /* Namespace Lexcer */ -- cgit v1.3.1-26-gb76a