Página principal   Lista de namespaces   Hierarquia de classes   Lista de componentes   Lista de ficheiros   Componentes   Declarações  

simbolo.C

Ir para a documentação deste ficheiro.
00001 #include "simbolo.H"
00002 
00003 #include <sstream>
00004 
00005 using namespace std;
00006 
00007 Calculo::Simbolo::Simbolo(istream& entrada)
00008 {
00009     char c;
00010     if(entrada >> c)
00011         switch(c) {
00012           case '?':
00013             tipo_ = teste_de_condicao;
00014             break;
00015           case ':':
00016             tipo_ = separador_de_condicao;
00017             break;
00018           case '|':
00019             tipo_ = ou;
00020             break;
00021           case '&':
00022             tipo_ = e;
00023             break;
00024           case '=':
00025             c = ' ';
00026             if(not entrada.get(c) or c != '=')
00027                 throw ErroDeAnalise(string("símbolo '=' desconhecido: '=") + 
00028                                     c + '\'');
00029             tipo_ = igual;
00030             break;
00031           case '!':
00032             if(entrada.peek() == '=') {
00033                 tipo_ = diferente;
00034                 entrada.get();
00035             } else
00036                 tipo_ = negacao;
00037             break;
00038           case '<':
00039             if(entrada.peek() == '=') {
00040                 tipo_ = menor_ou_igual;
00041                 entrada.get();
00042             } else
00043                 tipo_ = menor;
00044             break;
00045           case '>':
00046             if(entrada.peek() == '=') {
00047                 tipo_ = maior_ou_igual;
00048                 entrada.get();
00049             } else
00050                 tipo_ = maior;
00051             break;
00052           case '+':
00053             tipo_ = adicao;
00054             break;
00055           case '-':
00056             tipo_ = subtraccao;
00057             break;
00058           case '*':
00059             tipo_ = produto;
00060             break;
00061           case '/':
00062             tipo_ = divisao;
00063             break;
00064           case '^':
00065             tipo_ = potencia;
00066             break;
00067           case '(':
00068             tipo_ = parenteses_esquerdo;
00069             break;
00070           case ')':
00071             tipo_ = parenteses_direito;
00072             break;
00073           case ',':
00074             tipo_ = virgula;
00075             break;
00076           case '%':
00077             leValorTextual(entrada);
00078             tipo_ = constante;
00079             break;
00080           default:
00081             entrada.putback(c);
00082             if(isdigit(c) or c == '.')
00083                 leValorNumerico(entrada);
00084             else if(isalpha(c)) {
00085                 leValorTextual(entrada);
00086                 tipo_ = identificador;
00087             } else
00088                 throw ErroDeAnalise(string("caractere '") + c + "' inválido");
00089             break;
00090         }
00091     else
00092         tipo_ = fim;
00093 
00094     assert(cumpreInvariante());
00095 }
00096 
00097 string Calculo::Simbolo::descricao() const 
00098 {
00099     assert(cumpreInvariante());
00100 
00101     ostringstream descricao;
00102     
00103     descricao << nomeCompleto();
00104     
00105     if(tipo_ == identificador or tipo_ == constante)
00106         descricao << " [valor = " << valorTextual() << ']'; 
00107     else if(tipo_ == numero)
00108         descricao << " [valor = " << valorNumerico() << ']'; 
00109     
00110     return descricao.str();
00111 }
00112 
00113 void Calculo::Simbolo::leValorTextual(istream& entrada)
00114 {
00115     valor_textual = "";
00116     char c;
00117 
00118     while(entrada.get(c) and (isalpha(c) or isdigit(c) or
00119                               c == '_'))
00120         valor_textual += c;
00121     if(entrada)
00122         entrada.putback(c);
00123 }
00124 
00125 string const Calculo::Simbolo::nomes_curtos_dos_tipos[fim + 1] =
00126     {
00127         "?", ":", 
00128         "|", "&", "!", 
00129         "==", "!=", 
00130         "<", "<=", 
00131         ">", ">=", 
00132         "+", "-", 
00133         "*", "/",
00134         "^", 
00135         "(", ")", 
00136         ",", 
00137         "id", "num", "const", 
00138         "fim"
00139     };
00140 
00141 string const Calculo::Simbolo::nomes_longos_dos_tipos[fim + 1] =
00142     {
00143         "teste de condição", "separador de condição", 
00144         "ou", "e", "negação", 
00145         "igual", "diferente", 
00146         "menor", "menor ou igual", 
00147         "maior", "maior ou igual", 
00148         "adição", "subtraccao", 
00149         "produto", "divisão",
00150         "potência", 
00151         "parênteses esquerdo", "parênteses direito", 
00152         "vírgula", 
00153         "identificador", "número", "constante", 
00154         "fim da entrada"
00155     };

Gerado em Mon Apr 15 15:57:08 2002 para Calculo por doxygen1.2.6 escrito por Dimitri van Heesch, © 1997-2001