Пример #1
0
        protected sealed override void ProcesarCadena(string cadena, MatchCollection coincidencias, DeclaraciónDeContexto declaración, int desplazamiento)
        {
            _coincidencia  = coincidencias[0];
            TipoDeVariable = CrearTipo();

            if (cadena.Length != _coincidencia.Value.Length)
            {
                throw new ErrorDeCompilación(
                          new ErrorDeDeclaración(
                              cadena,
                              string.Format(ERROR_TIPO_INVALIDO, TipoDeVariable.Nombre),
                              coincidencias[0].Index + desplazamiento,
                              cadena.Length));
            }

            if (declaración.VariablesDeclaradas.Where(v => v.Nombre == NombreDeVariable).Count() > 0)
            {
                throw new ErrorDeCompilación(
                          new ErrorDeDeclaración(
                              cadena,
                              ERROR_VARIABLE_EXISTENTE,
                              coincidencias[0].Index + desplazamiento,
                              cadena.Length));
            }

            var valorDeVariable = _coincidencia.Groups[NOMBRE_GRUPO_VALOR_DE_VARIABLE];

            if (string.IsNullOrEmpty(valorDeVariable.Value))
            {
                if (cadena.Contains(Lenguaje.OperadorDeAsignación))
                {
                    throw new ErrorDeCompilación(
                              new ErrorDeDeclaración(
                                  cadena,
                                  ERROR_DECLARACION_SIN_VALOR,
                                  coincidencias[0].Index + desplazamiento,
                                  cadena.Length));
                }
                //else
                //{
                //    var instrucción = new ApilarDato(TipoDeVariable.ValorPorDefecto, cadena)
                //    {
                //        Inicio = desplazamiento
                //    };
                //    declaración.Instrucciones.Enqueue(instrucción);
                //}
            }
            else
            {
                _evaluador.Procesar(valorDeVariable.Value, declaración, desplazamiento + valorDeVariable.Index);
                if (TipoDeVariable.Nombre != _evaluador.TipoDeSalida.Nombre)
                {
                    string mensaje = string.Format(ERROR_TIPO_INVALIDO, TipoDeVariable.Nombre);
                    throw new ErrorDeCompilación(
                              new ErrorDeDeclaración(
                                  cadena,
                                  mensaje,
                                  coincidencias[0].Index + desplazamiento,
                                  cadena.Length));
                }
            }

            CrearComportamiento(coincidencias[0].Value, declaración, desplazamiento);

            if (!string.IsNullOrEmpty(valorDeVariable.Value))
            {
                var cargarValorEnVariable = new CargarDatoEnVariable(NombreDeVariable, cadena)
                {
                    Inicio = desplazamiento
                };
                declaración.Instrucciones.Enqueue(cargarValorEnVariable);
            }
        }
        protected override void ProcesarCadena(string cadena, MatchCollection coincidencias, DeclaraciónDeContexto declaración, int desplazamiento)
        {
            //_evaluador = new ProcesadorDeEvaluación(Repositorio);
            var  nombreDeFunción = coincidencias[0].Groups[NOMBRE_GRUPO_NOMBRE_DE_FUNCION].Value;
            bool esNativa        = true;
            var  función         = declaración.FuncionesNativas[nombreDeFunción];

            if (función == null)
            {
                función  = declaración.Funciones[nombreDeFunción];
                esNativa = false;
            }

            if (función == null)
            {
                GenerarExcepción(cadena, ERROR_FUNCION_NO_ENCONTRADA, coincidencias[0].Index + desplazamiento, cadena.Length);
            }

            //Esto queda cerdo que no veas
            if (_evaluador == null)
            {
                _evaluador = new ProcesadorDeEvaluación(Repositorio);
            }

            int             índice             = función.Parámetros.Total - 1;
            string          subexpresion       = $@"{SEPARADORES}(?<valor>{FORMATO_VALIDO_VALOR_DE_INT}|{FORMATO_VALIDO_VALOR_DE_STRING}|{FORMATO_VALIDO_NOMBRE_DE_VARIABLE}){SEPARADORES}";
            Regex           separadorDeValores = new Regex($@"{SEPARADOR_DE_PARAMETROS}{subexpresion}");
            MatchCollection valoresEncontrados = separadorDeValores.Matches(SEPARADOR_DE_PARAMETROS + coincidencias[0].Groups[NOMBRE_GRUPO_PARAMETROS].Value);
            Stack <Match>   pilaDeValores      = new Stack <Match>();

            foreach (Match valorEncontrado in valoresEncontrados)
            {
                pilaDeValores.Push(valorEncontrado);
            }

            while (pilaDeValores.Count > 0)
            {
                Match coincidencia = pilaDeValores.Pop();
                var   valor        = coincidencia.Groups["valor"].Value;
                _evaluador.Procesar(valor, declaración, desplazamiento + coincidencias[0].Groups[NOMBRE_GRUPO_PARAMETROS].Index + coincidencia.Groups["valor"].Index - 1);
                var declaraciónDeParámetro = función.Parámetros[índice];
                if (declaraciónDeParámetro == null)
                {
                    GenerarExcepción(
                        valor,
                        "Parámetro no declarado",
                        coincidencias[0].Groups[NOMBRE_GRUPO_PARAMETROS].Index + desplazamiento + coincidencia.Groups["valor"].Index,
                        valor.Length);
                }
                else if (declaraciónDeParámetro.Tipo.Nombre != _evaluador.TipoDeSalida.Nombre)
                {
                    GenerarExcepción(
                        valor,
                        string.Format(ERROR_VALOR_DE_PARAMETRO_INVALIDO, declaraciónDeParámetro.Tipo.Nombre),
                        coincidencias[0].Groups[NOMBRE_GRUPO_PARAMETROS].Index + desplazamiento + coincidencia.Groups["valor"].Index,
                        valor.Length);
                }
                índice--;
            }

            _evaluador.TipoDeSalida = función.TipoDeRetorno;

            if (esNativa)
            {
                Instrucción instrucción = new LlamadaAFunciónNativa(nombreDeFunción, cadena)
                {
                    Inicio = desplazamiento
                };
                declaración.Instrucciones.Enqueue(instrucción);
            }
            else
            {
                Instrucción instrucción = new LlamadaAFunción(nombreDeFunción, cadena)
                {
                    Inicio = desplazamiento
                };
                declaración.Instrucciones.Enqueue(instrucción);
            }
        }