La propia librería te dirá como se procesan los errores. No tiene nada que ver con el lenguaje.
Esta sección te permite ver todos los mensajes escritos por este usuario. Ten en cuenta que sólo puedes ver los mensajes escritos en zonas a las que tienes acceso en este momento.
Mostrar Mensajes Menúint b;
ofstream escritura("texto.bin");
escritura.write((char*) &b,sizeof(int));
int b;
ifstream escritura("texto.bin");
escritura.read((char*) &b,sizeof(int));
getline(archivo,string);
Cita de: yoel_alejandro en 23 Marzo 2014, 02:51 AMNo solo necesitas un compilador que soporte C++11 sino que también tienes que activar ese modo en la compilación (creo que era std=C++11 o algo así).
Gracias por el token = c !!!
Ahora dos detallitos:
(1) Si podrías hacer el código más portable, que no requiera necesariamente C++11. Yo uso Ubuntu 10.04, de 2010, y g++ no está actualizado a 2011. Tengo problemas con el "auto it", en el otro código tive que cambiar todas las expresiones de ese tipo al tipo "class<T> :: it". Quiero que sea portable porque la idea de ésto es primero usarlo como objeto académico-pedagógico en la Universidad por ejemplo, y no se si todos los estudiantes están actualizado a la última versión del software.
Cita de: yoel_alejandro en 23 Marzo 2014, 02:51 AM(2) La invocación de la conversión a número empieza cuando se detecta un carácter entre '0' y '9', no con el signo '+' ó '-'. ¿Eso no hará que por ejemplo al recibir 2 * -3, lo interprete como 2 * 3?Efective wonder.
const string operators[N_operators] = {"+", "-", "*", "/", "%", "^"};
const char operators[N_operators] = {'+','-','*','/','%','^'};
void hilo(int a,int b)
{
cout<<a<<b<<endl;
}
void otro_hilo(double a,float b,float c)
{
a += b/c;
cout<<a<<endl;
}
int main()
{
thread t1(hilo,1,2); // llamo a la funcion hilo con los argumentos 1 y 2
thread t2(otro_hilo,3.2,12.5,6.1); // llamo a la funcion otro_hilo con los argumentos 3.2, 12.5 y 6.1
t1.join();
t2.join();
}
/* es un carácter numérico: pasar al posfijo */
if ( c >= '0' && c <= '9' )
{
cout << "\tes numero: pasado a posfijo" << endl << endl;
postfix = postfix + " " + c;
continue;
}
/* es un carácter numérico: pasar al posfijo */
if ( c >= '0' && c <= '9' )
{
double aux = ConvertirNumero(infix,i);
cout << "\tes numero: pasado a posfijo" << endl << endl;
result.push(aux);
continue;
}
#include <cstdlib>
#include <iostream>
#include <string>
#include <stack>
#include <cmath>
#include <list>
#include <sstream>
using namespace std;
/* Operadores matematicos */
#define N_operators 6
const string operators[N_operators] = {"+", "-", "*", "/", "%", "^"};
int precedences[N_operators] = {1, 1, 2, 2, 2, 3};
bool is_operator( const string );
int precedence( const string );
/* Mis sugerencias personales a este programa:
*
* - Considerar el cambio del nombre standby por aux_stack, u otro.
* - Incorporar el analizador lexico para expresiones numericas de punto
* flotante, o que ocupen mas de un caracter.
* - Eliminar la cadena intermedia postfix, pasando directamente los
* resultados de la pila de operadores extraidos de infix, a una pila
* de evaluacion.
* - Incorporar operadores unarios, como sin(), cos(), exp(), log(), etc.
* - Detectar errores de sintaxis en la expresion infija.
* - Otros que sean recomendados.
*/
double ConvertirNumero(string &Entrada,int &Index)
{
list<double> Enteros;
list<double> Decimales;
short aux;
short signo = 1;
// Nos saltamos los espacios en blanco
while(Entrada[Index] == ' ')
{
Index++;
}
if (Entrada[Index] == '-')
{
signo = -1;
Index++;
}
/** Ahora debería haber números, de lo contrario tenemos un error **/
if (Entrada[Index] < '0' || Entrada[Index] > '9')
{
stringstream buffer;
buffer<<"Error de sintaxis, desconocido elemento: '"<<Entrada[Index]<<"' en la posicion: "<<Index+1;
throw buffer.str().c_str();
}
/** Añadimos los enteros **/
while (Entrada[Index] >= '0' && Entrada[Index] <= '9' && Index < Entrada.size())
{
Enteros.push_back(Entrada[Index]-48);
//cout<<Cosa[i]<<endl;
Index++;
}
/** Si a continuación encontramos un punto o una coma, esque hay numeros a continuacion **/
if (Entrada[Index] == '.' || Entrada[Index] == ',')
{
bool Activado = false;
Index++;
while (Entrada[Index] >= '0' && Entrada[Index] <= '9' && Index < Entrada.size())
{
Decimales.push_back(Entrada[Index]-48);
Index++;
Activado = true;
}
if (!Activado)
{
throw "Error de sintaxis, se insertó un punto pero no se añadió ningun decimal";
}
}
double Numero = 0; // El valor que devolveremos
aux = 0;
/** Recorremos los enteros y lo pasamos a número. Como tenemos las cifras simplemente es sumarlas **/
for (auto it = Enteros.begin(); it != Enteros.end(); it++)
{
Numero += *it*pow(10,Enteros.size()-aux-1);
aux++;
}
aux = 0;
/** Idem, pero para los decimales **/
if (!Decimales.empty())
for (auto it = Decimales.begin(); it != Decimales.end(); it++)
{
Numero += *it/(pow(10,(aux))*10);
aux++;
}
Numero *= signo;
Index--;
return Numero;
}
int main()
{
string infix, postfix, token;
stack <string> standby;
stack <double> result;
int i;
char c;
double A, B;
/* Cadena de entrada */
cout << "Intro expresion infija: ">
getline( cin, infix );
cout << endl;
/*************************************************************
PRIMERA PARTE: Procesar la cadena infijo, y crear posfijo
*************************************************************/
for ( i = 0; i < infix.size(); i++ )
{
/* esto debe cambiar luego a un token o palabra devuelta por
* el analizador léxico */
c = infix[i];
token.clear();
token += c; /* parece burdo, pero no conozco mejor manera de
* crear un string a partir de un unico caracter */
/* es un espacio: despreciar */
if ( c == ' ' ) continue;
cout << "Analizando token: '" << c << "'" << endl;
if ( c >= '0' && c <= '9' )
{
cout<<"Init: "<<i<<endl;
double aux = ConvertirNumero(infix,i);
cout<<"finit: "<<i<<endl;
cout << "\tes numero: pasado a posfijo:" << aux<<endl << endl;
result.push(aux);
// esto es solo para la depuracion
stringstream cosa;
cosa<<aux;
postfix = postfix + " " + cosa.str();
continue;
}
/* si se lee un operador: sacar de la pila y pasar al postfijo
* todos los operadores con una precedencia mayor o igual a la
* suya, y depositar el mismo en la pila */
if ( is_operator( token ) )
{
cout << "\tes operador:" << endl;
while ( !standby.empty() && precedence( standby.top() )
>= precedence( token ) )
{
cout << "\tpasado operador '" + standby.top() +
"' de la pila a posfijo" << endl;
postfix = postfix + " " + standby.top();
standby.pop();
}
standby.push( token );
cout << "\tcolocar '" << token << "' en la pila" << endl << endl;
continue;
}
/* si se lee "(": colocar en la pila */
if ( token == "(" )
{
cout << "pasado a posfijo" << endl << endl;
standby.push( token );
continue;
}
/* si se lee ")": retirar de la pila hasta encontrar '(', y pasar
* los elementos retirados a posfijo, luego descartar el "(" */
if ( token == ")" )
{
while ( !standby.empty() && standby.top() != "(" )
{
cout << "\tpasado operador '" + standby.top() +
"' de la pila a posfijo" << endl << endl;
postfix = postfix + " " + standby.top();
standby.pop();
}
if ( !standby.empty() )
standby.pop(); /* descartar el "(" */
}
}
/* extraer de la pila cualquier operador restante y pasarlo a la cadena posfijo */
while ( !standby.empty() )
{
cout << "Pasado operador '" + standby.top() +
"' de la pila a posfijo" << endl << endl;
postfix = postfix + " " + standby.top();
standby.pop();
}
/* Imprimir el posfijo */
cout << "Posfijo es: \n\t" << postfix << endl << endl;
/****************************************************************
SEGUNDA PARTE: Procesar la cadena posfijo, y devolver resultado
****************************************************************/
A = 0;
cout << "Evaluando la expresion ..." << endl;
for ( i = 0; i < postfix.size(); i++ )
{
c = postfix[i];
token.clear();
token += c;
/* si se lee un operando (caracter numerico), depositar en la pila */
if ( c >= '0' && c <= '9' )
{
continue;
}
/* si se lee un operador binario, poner en A y B los últimos dos argumentos
* de la pila y operarlos, guardando el resultado en la pila */
if ( is_operator( token ) )
{
if ( !result.empty() )
{
B = result.top();
result.pop();
}
else
{
cout << "Argumentos insuficientes para '" << c << "'" << endl;
return -1;
}
if ( !result.empty() )
{
A = result.top();
result.pop();
}
else
{
cout << "Argumentos insuficientes para '" << c << "'" << endl;
return -1;
}
cout << "\toperar " << A << token << B << " = ";
if ( token == "+" )
{
A += B;
result.push( A );
}
else if ( token == "-" )
{
A -= B;
result.push( A );
}
else if ( token == "*" )
{
A *= B;
result.push( A );
}
else if ( token == "/" )
{
A /= B;
result.push( A );
}
else if ( token == "%" )
{
A = (int )A % (int )B;
result.push( A );
}
else if ( token == "^" )
{
A = pow(A, B);
result.push( A );
}
cout << A << endl;
}
}
if ( !result.empty() )
cout << endl << "El resultado es: " << result.top() << endl;
return 0;
}
/* Verdadero si el token corresponde a un operador. */
bool is_operator( const string token )
{
for ( int i = 0; i < N_operators; i++ )
if ( operators[i] == token )
return true;
return false;
}
/* Devuelve la precedencia del operador descrito por el
* string token (-1 si no es un operador) */
int precedence( const string token )
{
for ( int i = 0; i < N_operators; i++ )
if ( operators[i] == token )
return precedences[i];
return -1;
}
token.clear();
token += c;
token = c;