Tests passed.
--HG-- branch : feature
This commit is contained in:
parent
60ba211f2a
commit
d65368bafb
|
@ -102,7 +102,7 @@ CONFIG(debug, debug|release){
|
||||||
-Wmissing-include-dirs -Wpacked -Wredundant-decls -Winline \
|
-Wmissing-include-dirs -Wpacked -Wredundant-decls -Winline \
|
||||||
-Wswitch-default -Wswitch-enum -Wuninitialized -Wvariadic-macros \
|
-Wswitch-default -Wswitch-enum -Wuninitialized -Wvariadic-macros \
|
||||||
-Wlogical-op -Wnoexcept -Wmissing-noreturn -Wpointer-arith\
|
-Wlogical-op -Wnoexcept -Wmissing-noreturn -Wpointer-arith\
|
||||||
-Wstrict-null-sentinel -Wstrict-overflow=5 -Wundef -Wno-unused -gdwarf-3
|
-Wstrict-null-sentinel -Wstrict-overflow=5 -Wundef -Wno-unused -gdwarf-3 \
|
||||||
-ftrapv
|
-ftrapv
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -42,26 +42,26 @@ class VException : public QException
|
||||||
{
|
{
|
||||||
Q_DECLARE_TR_FUNCTIONS(VException)
|
Q_DECLARE_TR_FUNCTIONS(VException)
|
||||||
public:
|
public:
|
||||||
/**
|
/**
|
||||||
* @brief VException constructor exception
|
* @brief VException constructor exception
|
||||||
* @param what string with error
|
* @param what string with error
|
||||||
*/
|
*/
|
||||||
VException(const QString &what);
|
VException(const QString &what);
|
||||||
/**
|
/**
|
||||||
* @brief VException copy constructor
|
* @brief VException copy constructor
|
||||||
* @param e exception
|
* @param e exception
|
||||||
*/
|
*/
|
||||||
VException(const VException &e);
|
VException(const VException &e);
|
||||||
virtual ~VException() noexcept (true){}
|
virtual ~VException() noexcept (true){}
|
||||||
/**
|
/**
|
||||||
* @brief raise method raise for exception
|
* @brief raise method raise for exception
|
||||||
*/
|
*/
|
||||||
void raise() const;
|
virtual void raise() const;
|
||||||
/**
|
/**
|
||||||
* @brief clone clone exception
|
* @brief clone clone exception
|
||||||
* @return new exception
|
* @return new exception
|
||||||
*/
|
*/
|
||||||
VException *clone() const;
|
virtual VException *clone() const;
|
||||||
/**
|
/**
|
||||||
* @brief ErrorMessage return main error message
|
* @brief ErrorMessage return main error message
|
||||||
* @return error message
|
* @return error message
|
||||||
|
|
|
@ -74,8 +74,9 @@ void noisyFailureMsgHandler(QtMsgType type, const QMessageLogContext &context, c
|
||||||
switch (type)
|
switch (type)
|
||||||
{
|
{
|
||||||
case QtDebugMsg:
|
case QtDebugMsg:
|
||||||
fprintf(stderr, "Debug: %s (%s:%u, %s)\n", localMsg.constData(), context.file, context.line,
|
fprintf(stderr, "Debug: %s\n", localMsg.constData());
|
||||||
context.function);
|
// fprintf(stderr, "Debug: %s (%s:%u, %s)\n", localMsg.constData(), context.file, context.line,
|
||||||
|
// context.function);
|
||||||
return;
|
return;
|
||||||
case QtWarningMsg:
|
case QtWarningMsg:
|
||||||
messageBox.setIcon(QMessageBox::Warning);
|
messageBox.setIcon(QMessageBox::Warning);
|
||||||
|
|
|
@ -131,7 +131,7 @@ qreal QmuParser::Sum(const qreal *a_afArg, int a_iArgc)
|
||||||
{
|
{
|
||||||
if (a_iArgc == false)
|
if (a_iArgc == false)
|
||||||
{
|
{
|
||||||
throw exception_type("too few arguments for function sum.");
|
throw QmuParserError("too few arguments for function sum.");
|
||||||
}
|
}
|
||||||
qreal fRes=0;
|
qreal fRes=0;
|
||||||
for (int i=0; i<a_iArgc; ++i)
|
for (int i=0; i<a_iArgc; ++i)
|
||||||
|
@ -151,7 +151,7 @@ qreal QmuParser::Avg(const qreal *a_afArg, int a_iArgc)
|
||||||
{
|
{
|
||||||
if (a_iArgc == false)
|
if (a_iArgc == false)
|
||||||
{
|
{
|
||||||
throw exception_type("too few arguments for function sum.");
|
throw QmuParserError("too few arguments for function sum.");
|
||||||
}
|
}
|
||||||
qreal fRes=0;
|
qreal fRes=0;
|
||||||
for (int i=0; i<a_iArgc; ++i)
|
for (int i=0; i<a_iArgc; ++i)
|
||||||
|
@ -171,7 +171,7 @@ qreal QmuParser::Min(const qreal *a_afArg, int a_iArgc)
|
||||||
{
|
{
|
||||||
if (a_iArgc == false)
|
if (a_iArgc == false)
|
||||||
{
|
{
|
||||||
throw exception_type("too few arguments for function min.");
|
throw QmuParserError("too few arguments for function min.");
|
||||||
}
|
}
|
||||||
qreal fRes=a_afArg[0];
|
qreal fRes=a_afArg[0];
|
||||||
for (int i=0; i<a_iArgc; ++i)
|
for (int i=0; i<a_iArgc; ++i)
|
||||||
|
@ -191,7 +191,7 @@ qreal QmuParser::Max(const qreal *a_afArg, int a_iArgc)
|
||||||
{
|
{
|
||||||
if (a_iArgc == false)
|
if (a_iArgc == false)
|
||||||
{
|
{
|
||||||
throw exception_type("too few arguments for function min.");
|
throw QmuParserError("too few arguments for function min.");
|
||||||
}
|
}
|
||||||
qreal fRes=a_afArg[0];
|
qreal fRes=a_afArg[0];
|
||||||
for (int i=0; i<a_iArgc; ++i)
|
for (int i=0; i<a_iArgc; ++i)
|
||||||
|
|
|
@ -53,7 +53,7 @@ HEADERS += \
|
||||||
qmuparsertest.h \
|
qmuparsertest.h \
|
||||||
stable.h
|
stable.h
|
||||||
|
|
||||||
VERSION = 2.2.3
|
VERSION = 2.2.4
|
||||||
|
|
||||||
unix {
|
unix {
|
||||||
target.path = /usr/lib
|
target.path = /usr/lib
|
||||||
|
@ -83,7 +83,7 @@ CONFIG(debug, debug|release){
|
||||||
-Wmissing-include-dirs -Wpacked -Wredundant-decls -Winline \
|
-Wmissing-include-dirs -Wpacked -Wredundant-decls -Winline \
|
||||||
-Wswitch-default -Wswitch-enum -Wuninitialized -Wvariadic-macros \
|
-Wswitch-default -Wswitch-enum -Wuninitialized -Wvariadic-macros \
|
||||||
-Wlogical-op -Wnoexcept -Wmissing-noreturn -Wpointer-arith\
|
-Wlogical-op -Wnoexcept -Wmissing-noreturn -Wpointer-arith\
|
||||||
-Wstrict-null-sentinel -Wstrict-overflow=5 -Wundef -Wno-unused -gdwarf-3
|
-Wstrict-null-sentinel -Wstrict-overflow=5 -Wundef -Wno-unused -gdwarf-3 \
|
||||||
-ftrapv
|
-ftrapv
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -27,6 +27,9 @@
|
||||||
#include <omp.h>
|
#include <omp.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#include "qmuparsererror.h"
|
||||||
|
#include "qmuparsertokenreader.h"
|
||||||
|
|
||||||
using namespace std;
|
using namespace std;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -438,19 +441,19 @@ void QmuParserBase::CheckOprt(const QString &a_sName, const QmuParserCallback &a
|
||||||
Q_UNREACHABLE();
|
Q_UNREACHABLE();
|
||||||
break;
|
break;
|
||||||
case cmVARPOW2:
|
case cmVARPOW2:
|
||||||
Q_UNREACHABLE();
|
// For optimization purposes
|
||||||
break;
|
break;
|
||||||
case cmVARPOW3:
|
case cmVARPOW3:
|
||||||
Q_UNREACHABLE();
|
// For optimization purposes
|
||||||
break;
|
break;
|
||||||
case cmVARPOW4:
|
case cmVARPOW4:
|
||||||
Q_UNREACHABLE();
|
// For optimization purposes
|
||||||
break;
|
break;
|
||||||
case cmVARMUL:
|
case cmVARMUL:
|
||||||
Q_UNREACHABLE();
|
// For optimization purposes
|
||||||
break;
|
break;
|
||||||
case cmPOW2:
|
case cmPOW2:
|
||||||
Q_UNREACHABLE();
|
// For optimization purposes
|
||||||
break;
|
break;
|
||||||
case cmFUNC:
|
case cmFUNC:
|
||||||
Q_UNREACHABLE();
|
Q_UNREACHABLE();
|
||||||
|
@ -937,7 +940,7 @@ const varmap_type& QmuParserBase::GetUsedVar() const
|
||||||
m_pParseFormula = &QmuParserBase::ParseString;
|
m_pParseFormula = &QmuParserBase::ParseString;
|
||||||
m_pTokenReader->IgnoreUndefVar(false);
|
m_pTokenReader->IgnoreUndefVar(false);
|
||||||
}
|
}
|
||||||
catch (const exception_type &e)
|
catch (const QmuParserError &e)
|
||||||
{
|
{
|
||||||
// Make sure to stay in string parse mode, dont call ReInit()
|
// Make sure to stay in string parse mode, dont call ReInit()
|
||||||
// because it deletes the array with the used variables
|
// because it deletes the array with the used variables
|
||||||
|
@ -995,7 +998,7 @@ const QString& QmuParserBase::GetExpr() const
|
||||||
/**
|
/**
|
||||||
* @brief Execute a function that takes a single string argument.
|
* @brief Execute a function that takes a single string argument.
|
||||||
* @param a_FunTok Function token.
|
* @param a_FunTok Function token.
|
||||||
* @throw exception_type If the function token is not a string function
|
* @throw QmuParserError If the function token is not a string function
|
||||||
*/
|
*/
|
||||||
QmuParserBase::token_type QmuParserBase::ApplyStrFunc(const token_type &a_FunTok,
|
QmuParserBase::token_type QmuParserBase::ApplyStrFunc(const token_type &a_FunTok,
|
||||||
const QVector<token_type> &a_vArg) const
|
const QVector<token_type> &a_vArg) const
|
||||||
|
@ -1052,7 +1055,7 @@ QmuParserBase::token_type QmuParserBase::ApplyStrFunc(const token_type &a_FunTok
|
||||||
* @param iArgCount Number of Arguments actually gathered used only for multiarg functions.
|
* @param iArgCount Number of Arguments actually gathered used only for multiarg functions.
|
||||||
* @post The result is pushed to the value stack
|
* @post The result is pushed to the value stack
|
||||||
* @post The function token is removed from the stack
|
* @post The function token is removed from the stack
|
||||||
* @throw exception_type if Argument count does not mach function requirements.
|
* @throw QmuParserError if Argument count does not mach function requirements.
|
||||||
*/
|
*/
|
||||||
void QmuParserBase::ApplyFunc( QStack<token_type> &a_stOpt, QStack<token_type> &a_stVal, int a_iArgCount) const
|
void QmuParserBase::ApplyFunc( QStack<token_type> &a_stOpt, QStack<token_type> &a_stVal, int a_iArgCount) const
|
||||||
{
|
{
|
||||||
|
@ -2051,7 +2054,7 @@ qreal QmuParserBase::ParseString() const
|
||||||
m_pParseFormula = &QmuParserBase::ParseCmdCode;
|
m_pParseFormula = &QmuParserBase::ParseCmdCode;
|
||||||
return (this->*m_pParseFormula)();
|
return (this->*m_pParseFormula)();
|
||||||
}
|
}
|
||||||
catch (QmuParserError &exc)
|
catch (qmu::QmuParserError &exc)
|
||||||
{
|
{
|
||||||
exc.SetFormula(m_pTokenReader->GetExpr());
|
exc.SetFormula(m_pTokenReader->GetExpr());
|
||||||
throw;
|
throw;
|
||||||
|
@ -2071,7 +2074,7 @@ qreal QmuParserBase::ParseString() const
|
||||||
*/
|
*/
|
||||||
void Q_NORETURN QmuParserBase::Error(EErrorCodes a_iErrc, int a_iPos, const QString &a_sTok) const
|
void Q_NORETURN QmuParserBase::Error(EErrorCodes a_iErrc, int a_iPos, const QString &a_sTok) const
|
||||||
{
|
{
|
||||||
throw exception_type(a_iErrc, a_sTok, m_pTokenReader->GetExpr(), a_iPos);
|
throw qmu::QmuParserError (a_iErrc, a_sTok, m_pTokenReader->GetExpr(), a_iPos);
|
||||||
}
|
}
|
||||||
|
|
||||||
//---------------------------------------------------------------------------------------------------------------------
|
//---------------------------------------------------------------------------------------------------------------------
|
||||||
|
|
|
@ -23,6 +23,7 @@
|
||||||
#ifndef QMUQPARSERBASE_H
|
#ifndef QMUQPARSERBASE_H
|
||||||
#define QMUQPARSERBASE_H
|
#define QMUQPARSERBASE_H
|
||||||
|
|
||||||
|
#include "qmuparser_global.h"
|
||||||
#include <QStack>
|
#include <QStack>
|
||||||
#include <QString>
|
#include <QString>
|
||||||
#include <QStringList>
|
#include <QStringList>
|
||||||
|
@ -51,17 +52,10 @@ namespace qmu
|
||||||
* Complementary to a set of internally implemented functions the parser is able to handle
|
* Complementary to a set of internally implemented functions the parser is able to handle
|
||||||
* user defined functions and variables.
|
* user defined functions and variables.
|
||||||
*/
|
*/
|
||||||
class QmuParserBase
|
class QMUPARSERSHARED_EXPORT QmuParserBase
|
||||||
{
|
{
|
||||||
friend class QmuParserTokenReader;
|
friend class QmuParserTokenReader;
|
||||||
public:
|
public:
|
||||||
/**
|
|
||||||
* @brief Type of the error class.
|
|
||||||
*
|
|
||||||
* Included for backwards compatibility.
|
|
||||||
*/
|
|
||||||
typedef QmuParserError exception_type;
|
|
||||||
|
|
||||||
QmuParserBase();
|
QmuParserBase();
|
||||||
QmuParserBase(const QmuParserBase &a_Parser);
|
QmuParserBase(const QmuParserBase &a_Parser);
|
||||||
QmuParserBase& operator=(const QmuParserBase &a_Parser) Q_DECL_NOEXCEPT;
|
QmuParserBase& operator=(const QmuParserBase &a_Parser) Q_DECL_NOEXCEPT;
|
||||||
|
@ -112,7 +106,7 @@ public:
|
||||||
const QString& ValidInfixOprtChars() const;
|
const QString& ValidInfixOprtChars() const;
|
||||||
void SetArgSep(char_type cArgSep);
|
void SetArgSep(char_type cArgSep);
|
||||||
QChar GetArgSep() const;
|
QChar GetArgSep() const;
|
||||||
void Error(EErrorCodes a_iErrc, int a_iPos = -1, const QString &a_strTok = QString() ) const;
|
void Q_NORETURN Error(EErrorCodes a_iErrc, int a_iPos = -1, const QString &a_strTok = QString() ) const;
|
||||||
/**
|
/**
|
||||||
* @fn void qmu::QmuParserBase::DefineFun(const string_type &a_strName, fun_type0 a_pFun,
|
* @fn void qmu::QmuParserBase::DefineFun(const string_type &a_strName, fun_type0 a_pFun,
|
||||||
* bool a_bAllowOpt = true)
|
* bool a_bAllowOpt = true)
|
||||||
|
|
|
@ -430,10 +430,8 @@ void QmuParserByteCode::AddOp(ECmdCode a_Oprt)
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case cmLE:
|
case cmLE:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmGE:
|
case cmGE:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmNEQ:
|
case cmNEQ:
|
||||||
Q_UNREACHABLE();
|
Q_UNREACHABLE();
|
||||||
|
@ -442,13 +440,10 @@ void QmuParserByteCode::AddOp(ECmdCode a_Oprt)
|
||||||
Q_UNREACHABLE();
|
Q_UNREACHABLE();
|
||||||
break;
|
break;
|
||||||
case cmLT:
|
case cmLT:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmGT:
|
case cmGT:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmLAND:
|
case cmLAND:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmLOR:
|
case cmLOR:
|
||||||
Q_UNREACHABLE();
|
Q_UNREACHABLE();
|
||||||
|
@ -670,10 +665,8 @@ void QmuParserByteCode::Finalize() Q_DECL_NOEXCEPT
|
||||||
m_vRPN[idx].Oprt.offset = i - idx;
|
m_vRPN[idx].Oprt.offset = i - idx;
|
||||||
break;
|
break;
|
||||||
case cmLE:
|
case cmLE:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmGE:
|
case cmGE:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmNEQ:
|
case cmNEQ:
|
||||||
Q_UNREACHABLE();
|
Q_UNREACHABLE();
|
||||||
|
@ -682,34 +675,25 @@ void QmuParserByteCode::Finalize() Q_DECL_NOEXCEPT
|
||||||
Q_UNREACHABLE();
|
Q_UNREACHABLE();
|
||||||
break;
|
break;
|
||||||
case cmLT:
|
case cmLT:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmGT:
|
case cmGT:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmADD:
|
case cmADD:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmSUB:
|
case cmSUB:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmMUL:
|
case cmMUL:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmDIV:
|
case cmDIV:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmPOW:
|
case cmPOW:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmLAND:
|
case cmLAND:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmLOR:
|
case cmLOR:
|
||||||
Q_UNREACHABLE();
|
Q_UNREACHABLE();
|
||||||
break;
|
break;
|
||||||
case cmASSIGN:
|
case cmASSIGN:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmBO:
|
case cmBO:
|
||||||
Q_UNREACHABLE();
|
Q_UNREACHABLE();
|
||||||
|
@ -721,31 +705,27 @@ void QmuParserByteCode::Finalize() Q_DECL_NOEXCEPT
|
||||||
Q_UNREACHABLE();
|
Q_UNREACHABLE();
|
||||||
break;
|
break;
|
||||||
case cmVAR:
|
case cmVAR:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmVAL:
|
case cmVAL:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmVARPOW2:
|
case cmVARPOW2:
|
||||||
Q_UNREACHABLE();
|
// For optimization purposes
|
||||||
break;
|
break;
|
||||||
case cmVARPOW3:
|
case cmVARPOW3:
|
||||||
Q_UNREACHABLE();
|
// For optimization purposes
|
||||||
break;
|
break;
|
||||||
case cmVARPOW4:
|
case cmVARPOW4:
|
||||||
Q_UNREACHABLE();
|
// For optimization purposes
|
||||||
break;
|
break;
|
||||||
case cmVARMUL:
|
case cmVARMUL:
|
||||||
Q_UNREACHABLE();
|
// For optimization purposes
|
||||||
break;
|
break;
|
||||||
case cmPOW2:
|
case cmPOW2:
|
||||||
Q_UNREACHABLE();
|
// For optimization purposes
|
||||||
break;
|
break;
|
||||||
case cmFUNC:
|
case cmFUNC:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmFUNC_STR:
|
case cmFUNC_STR:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmFUNC_BULK:
|
case cmFUNC_BULK:
|
||||||
Q_UNREACHABLE();
|
Q_UNREACHABLE();
|
||||||
|
@ -763,7 +743,6 @@ void QmuParserByteCode::Finalize() Q_DECL_NOEXCEPT
|
||||||
Q_UNREACHABLE();
|
Q_UNREACHABLE();
|
||||||
break;
|
break;
|
||||||
case cmEND:
|
case cmEND:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
break;
|
||||||
case cmUNKNOWN:
|
case cmUNKNOWN:
|
||||||
Q_UNREACHABLE();
|
Q_UNREACHABLE();
|
||||||
|
|
|
@ -109,7 +109,7 @@ QmuParserErrorMsg::QmuParserErrorMsg()
|
||||||
* @brief Default constructor.
|
* @brief Default constructor.
|
||||||
*/
|
*/
|
||||||
QmuParserError::QmuParserError()
|
QmuParserError::QmuParserError()
|
||||||
: m_sMsg(), m_sExpr(), m_sTok(), m_iPos ( -1 ), m_iErrc ( ecUNDEFINED ),
|
: QException(), m_sMsg(), m_sExpr(), m_sTok(), m_iPos ( -1 ), m_iErrc ( ecUNDEFINED ),
|
||||||
m_ErrMsg ( QmuParserErrorMsg::Instance() )
|
m_ErrMsg ( QmuParserErrorMsg::Instance() )
|
||||||
{}
|
{}
|
||||||
|
|
||||||
|
@ -120,7 +120,7 @@ QmuParserError::QmuParserError()
|
||||||
* It does not contain any information but the error code.
|
* It does not contain any information but the error code.
|
||||||
*/
|
*/
|
||||||
QmuParserError::QmuParserError ( EErrorCodes a_iErrc )
|
QmuParserError::QmuParserError ( EErrorCodes a_iErrc )
|
||||||
: m_sMsg(), m_sExpr(), m_sTok(), m_iPos ( -1 ), m_iErrc ( a_iErrc ),
|
: QException(), m_sMsg(), m_sExpr(), m_sTok(), m_iPos ( -1 ), m_iErrc ( a_iErrc ),
|
||||||
m_ErrMsg ( QmuParserErrorMsg::Instance() )
|
m_ErrMsg ( QmuParserErrorMsg::Instance() )
|
||||||
{
|
{
|
||||||
m_sMsg = m_ErrMsg[m_iErrc];
|
m_sMsg = m_ErrMsg[m_iErrc];
|
||||||
|
@ -133,7 +133,7 @@ QmuParserError::QmuParserError ( EErrorCodes a_iErrc )
|
||||||
* @brief Construct an error from a message text.
|
* @brief Construct an error from a message text.
|
||||||
*/
|
*/
|
||||||
QmuParserError::QmuParserError ( const QString &sMsg )
|
QmuParserError::QmuParserError ( const QString &sMsg )
|
||||||
: m_sMsg(sMsg), m_sExpr(), m_sTok(), m_iPos ( -1 ), m_iErrc ( ecUNDEFINED ),
|
: QException(), m_sMsg(sMsg), m_sExpr(), m_sTok(), m_iPos ( -1 ), m_iErrc ( ecUNDEFINED ),
|
||||||
m_ErrMsg ( QmuParserErrorMsg::Instance() )
|
m_ErrMsg ( QmuParserErrorMsg::Instance() )
|
||||||
{}
|
{}
|
||||||
|
|
||||||
|
@ -146,7 +146,7 @@ QmuParserError::QmuParserError ( const QString &sMsg )
|
||||||
* @param [in] a_iPos the position in the expression where the error occured.
|
* @param [in] a_iPos the position in the expression where the error occured.
|
||||||
*/
|
*/
|
||||||
QmuParserError::QmuParserError ( EErrorCodes iErrc, const QString &sTok, const QString &sExpr, int iPos )
|
QmuParserError::QmuParserError ( EErrorCodes iErrc, const QString &sTok, const QString &sExpr, int iPos )
|
||||||
: m_sMsg(), m_sExpr ( sExpr ), m_sTok ( sTok ), m_iPos ( iPos ), m_iErrc ( iErrc ),
|
: QException(), m_sMsg(), m_sExpr ( sExpr ), m_sTok ( sTok ), m_iPos ( iPos ), m_iErrc ( iErrc ),
|
||||||
m_ErrMsg ( QmuParserErrorMsg::Instance() )
|
m_ErrMsg ( QmuParserErrorMsg::Instance() )
|
||||||
{
|
{
|
||||||
m_sMsg = m_ErrMsg[m_iErrc];
|
m_sMsg = m_ErrMsg[m_iErrc];
|
||||||
|
@ -162,7 +162,7 @@ QmuParserError::QmuParserError ( EErrorCodes iErrc, const QString &sTok, const Q
|
||||||
* @param [in] sTok The token string related to this error.
|
* @param [in] sTok The token string related to this error.
|
||||||
*/
|
*/
|
||||||
QmuParserError::QmuParserError ( EErrorCodes a_iErrc, int a_iPos, const QString &sTok )
|
QmuParserError::QmuParserError ( EErrorCodes a_iErrc, int a_iPos, const QString &sTok )
|
||||||
: m_sMsg(), m_sExpr(), m_sTok ( sTok ), m_iPos ( a_iPos ), m_iErrc ( a_iErrc ),
|
: QException(), m_sMsg(), m_sExpr(), m_sTok ( sTok ), m_iPos ( a_iPos ), m_iErrc ( a_iErrc ),
|
||||||
m_ErrMsg ( QmuParserErrorMsg::Instance() )
|
m_ErrMsg ( QmuParserErrorMsg::Instance() )
|
||||||
{
|
{
|
||||||
m_sMsg = m_ErrMsg[m_iErrc];
|
m_sMsg = m_ErrMsg[m_iErrc];
|
||||||
|
@ -177,7 +177,7 @@ QmuParserError::QmuParserError ( EErrorCodes a_iErrc, int a_iPos, const QString
|
||||||
* @param [in] sTok The token string related to this error.
|
* @param [in] sTok The token string related to this error.
|
||||||
*/
|
*/
|
||||||
QmuParserError::QmuParserError ( const QString &szMsg, int iPos, const QString &sTok )
|
QmuParserError::QmuParserError ( const QString &szMsg, int iPos, const QString &sTok )
|
||||||
: m_sMsg ( szMsg ), m_sExpr(), m_sTok ( sTok ), m_iPos ( iPos ), m_iErrc ( ecGENERIC ),
|
: QException(), m_sMsg ( szMsg ), m_sExpr(), m_sTok ( sTok ), m_iPos ( iPos ), m_iErrc ( ecGENERIC ),
|
||||||
m_ErrMsg ( QmuParserErrorMsg::Instance() )
|
m_ErrMsg ( QmuParserErrorMsg::Instance() )
|
||||||
{
|
{
|
||||||
ReplaceSubString ( m_sMsg, "$POS$", QString().setNum ( m_iPos ) );
|
ReplaceSubString ( m_sMsg, "$POS$", QString().setNum ( m_iPos ) );
|
||||||
|
@ -187,7 +187,7 @@ QmuParserError::QmuParserError ( const QString &szMsg, int iPos, const QString &
|
||||||
//---------------------------------------------------------------------------------------------------------------------
|
//---------------------------------------------------------------------------------------------------------------------
|
||||||
/** @brief Copy constructor. */
|
/** @brief Copy constructor. */
|
||||||
QmuParserError::QmuParserError ( const QmuParserError &a_Obj )
|
QmuParserError::QmuParserError ( const QmuParserError &a_Obj )
|
||||||
: m_sMsg ( a_Obj.m_sMsg ), m_sExpr ( a_Obj.m_sExpr ), m_sTok ( a_Obj.m_sTok ),
|
: QException(), m_sMsg ( a_Obj.m_sMsg ), m_sExpr ( a_Obj.m_sExpr ), m_sTok ( a_Obj.m_sTok ),
|
||||||
m_iPos ( a_Obj.m_iPos ), m_iErrc ( a_Obj.m_iErrc ), m_ErrMsg ( QmuParserErrorMsg::Instance() )
|
m_iPos ( a_Obj.m_iPos ), m_iErrc ( a_Obj.m_iErrc ), m_ErrMsg ( QmuParserErrorMsg::Instance() )
|
||||||
{}
|
{}
|
||||||
|
|
||||||
|
@ -208,10 +208,6 @@ QmuParserError& QmuParserError::operator= ( const QmuParserError &a_Obj )
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
|
||||||
//---------------------------------------------------------------------------------------------------------------------
|
|
||||||
QmuParserError::~QmuParserError()
|
|
||||||
{}
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------------------------------------------------
|
//---------------------------------------------------------------------------------------------------------------------
|
||||||
/**
|
/**
|
||||||
* @brief Replace all ocuurences of a substring with another string.
|
* @brief Replace all ocuurences of a substring with another string.
|
||||||
|
@ -309,4 +305,5 @@ EErrorCodes QmuParserError::GetCode() const
|
||||||
{
|
{
|
||||||
return m_iErrc;
|
return m_iErrc;
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace qmu
|
} // namespace qmu
|
||||||
|
|
|
@ -23,11 +23,9 @@
|
||||||
#ifndef QMUPARSERERROR_H
|
#ifndef QMUPARSERERROR_H
|
||||||
#define QMUPARSERERROR_H
|
#define QMUPARSERERROR_H
|
||||||
|
|
||||||
#include <cassert>
|
#include "qmuparser_global.h"
|
||||||
#include <stdexcept>
|
|
||||||
#include <string>
|
|
||||||
#include <sstream>
|
#include <sstream>
|
||||||
#include <memory>
|
#include <QException>
|
||||||
|
|
||||||
#include "qmuparserdef.h"
|
#include "qmuparserdef.h"
|
||||||
|
|
||||||
|
@ -117,10 +115,9 @@ private:
|
||||||
|
|
||||||
Part of the math parser package.
|
Part of the math parser package.
|
||||||
*/
|
*/
|
||||||
class QmuParserError
|
class QMUPARSERSHARED_EXPORT QmuParserError : public QException
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
|
|
||||||
QmuParserError();
|
QmuParserError();
|
||||||
explicit QmuParserError ( EErrorCodes a_iErrc );
|
explicit QmuParserError ( EErrorCodes a_iErrc );
|
||||||
explicit QmuParserError ( const QString &sMsg );
|
explicit QmuParserError ( const QString &sMsg );
|
||||||
|
@ -129,7 +126,7 @@ public:
|
||||||
QmuParserError ( const QString &a_szMsg, int a_iPos, const QString &sTok = QString() );
|
QmuParserError ( const QString &a_szMsg, int a_iPos, const QString &sTok = QString() );
|
||||||
QmuParserError ( const QmuParserError &a_Obj );
|
QmuParserError ( const QmuParserError &a_Obj );
|
||||||
QmuParserError& operator= ( const QmuParserError &a_Obj );
|
QmuParserError& operator= ( const QmuParserError &a_Obj );
|
||||||
~QmuParserError();
|
virtual ~QmuParserError() noexcept (true){}
|
||||||
|
|
||||||
void SetFormula ( const QString &a_strFormula );
|
void SetFormula ( const QString &a_strFormula );
|
||||||
const QString& GetExpr() const;
|
const QString& GetExpr() const;
|
||||||
|
@ -138,6 +135,15 @@ public:
|
||||||
const QString& GetToken() const;
|
const QString& GetToken() const;
|
||||||
EErrorCodes GetCode() const;
|
EErrorCodes GetCode() const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief raise method raise for exception
|
||||||
|
*/
|
||||||
|
virtual void raise() const;
|
||||||
|
/**
|
||||||
|
* @brief clone clone exception
|
||||||
|
* @return new exception
|
||||||
|
*/
|
||||||
|
virtual QmuParserError *clone() const;
|
||||||
private:
|
private:
|
||||||
QString m_sMsg; ///< The message string
|
QString m_sMsg; ///< The message string
|
||||||
QString m_sExpr; ///< Formula string
|
QString m_sExpr; ///< Formula string
|
||||||
|
@ -152,6 +158,16 @@ private:
|
||||||
void Reset();
|
void Reset();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
inline void QmuParserError::raise() const
|
||||||
|
{
|
||||||
|
throw *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline QmuParserError *QmuParserError::clone() const
|
||||||
|
{
|
||||||
|
return new QmuParserError(*this);
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace qmu
|
} // namespace qmu
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -23,10 +23,8 @@
|
||||||
#include "qmuparsertest.h"
|
#include "qmuparsertest.h"
|
||||||
#include <QtMath>
|
#include <QtMath>
|
||||||
#include <QString>
|
#include <QString>
|
||||||
|
#include <QDebug>
|
||||||
#include <cstdio>
|
#include "qmuparsererror.h"
|
||||||
#include <iostream>
|
|
||||||
#include <limits>
|
|
||||||
|
|
||||||
using namespace std;
|
using namespace std;
|
||||||
|
|
||||||
|
@ -64,32 +62,33 @@ QmuParserTester::QmuParserTester()
|
||||||
//---------------------------------------------------------------------------------------------------------------------
|
//---------------------------------------------------------------------------------------------------------------------
|
||||||
int QmuParserTester::IsHexVal ( const QString &a_szExpr, int *a_iPos, qreal *a_fVal )
|
int QmuParserTester::IsHexVal ( const QString &a_szExpr, int *a_iPos, qreal *a_fVal )
|
||||||
{
|
{
|
||||||
if ( a_szExpr[1] == 0 || ( a_szExpr[0] != '0' || a_szExpr[1] != 'x' ) )
|
if ( a_szExpr.data()[1] == 0 || ( a_szExpr.data()[0] != '0' || a_szExpr.data()[1] != 'x' ) )
|
||||||
{
|
{
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
unsigned iVal ( 0 );
|
unsigned iVal ( 0 );
|
||||||
bool ok = false;
|
|
||||||
iVal = a_szExpr.toUInt ( &ok, 16 );
|
|
||||||
|
|
||||||
if ( ok )
|
#if defined(_UNICODE)
|
||||||
|
std::wstring a_szExprStd = a_szExpr.mid(2).toStdWString();
|
||||||
|
#else
|
||||||
|
std::string a_szExprStd = a_szExpr.mid(2).toStdString();
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// New code based on streams for UNICODE compliance:
|
||||||
|
stringstream_type::pos_type nPos(0);
|
||||||
|
stringstream_type ss(a_szExprStd);
|
||||||
|
ss >> std::hex >> iVal;
|
||||||
|
nPos = ss.tellg();
|
||||||
|
|
||||||
|
if (nPos==static_cast<stringstream_type::pos_type>(0))
|
||||||
{
|
{
|
||||||
int nPos = a_szExpr.indexOf ( QString().setNum ( iVal, 16 ) );
|
|
||||||
if ( nPos == 0 )
|
|
||||||
{
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
*a_iPos += 2 + nPos;
|
|
||||||
*a_fVal = static_cast<qreal>(iVal);
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
else
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
*a_iPos += static_cast<int>(2 + nPos);
|
||||||
|
*a_fVal = static_cast<qreal>(iVal);
|
||||||
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
//---------------------------------------------------------------------------------------------------------------------
|
//---------------------------------------------------------------------------------------------------------------------
|
||||||
|
@ -128,11 +127,11 @@ int QmuParserTester::TestInterface()
|
||||||
|
|
||||||
if ( iStat == 0 )
|
if ( iStat == 0 )
|
||||||
{
|
{
|
||||||
qDebug() << "passed";
|
qDebug() << "TestInterface passed";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
qDebug() << "\n failed with " << iStat << " errors";
|
qDebug() << "\n TestInterface failed with " << iStat << " errors";
|
||||||
}
|
}
|
||||||
|
|
||||||
return iStat;
|
return iStat;
|
||||||
|
@ -157,11 +156,11 @@ int QmuParserTester::TestStrArg()
|
||||||
|
|
||||||
if ( iStat == 0 )
|
if ( iStat == 0 )
|
||||||
{
|
{
|
||||||
qDebug() << "passed";
|
qDebug() << "TestStrArg passed";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
qDebug() << "\n failed with " << iStat << " errors";
|
qDebug() << "\n TestStrArg failed with " << iStat << " errors";
|
||||||
}
|
}
|
||||||
|
|
||||||
return iStat;
|
return iStat;
|
||||||
|
@ -232,11 +231,11 @@ int QmuParserTester::TestBinOprt()
|
||||||
|
|
||||||
if ( iStat == 0 )
|
if ( iStat == 0 )
|
||||||
{
|
{
|
||||||
qDebug() << "passed";
|
qDebug() << "TestBinOprt passed";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
qDebug() << "\n failed with " << iStat << " errors";
|
qDebug() << "\n TestBinOprt failed with " << iStat << " errors";
|
||||||
}
|
}
|
||||||
|
|
||||||
return iStat;
|
return iStat;
|
||||||
|
@ -260,7 +259,7 @@ int QmuParserTester::TestNames()
|
||||||
{ \
|
{ \
|
||||||
p.Define##DOMAIN(EXPR, ARG); \
|
p.Define##DOMAIN(EXPR, ARG); \
|
||||||
} \
|
} \
|
||||||
catch (QmuParser::exception_type&) \
|
catch (QmuParserError &) \
|
||||||
{ \
|
{ \
|
||||||
iErr = (FAIL==false) ? 0 : 1; \
|
iErr = (FAIL==false) ? 0 : 1; \
|
||||||
} \
|
} \
|
||||||
|
@ -345,11 +344,11 @@ int QmuParserTester::TestNames()
|
||||||
|
|
||||||
if ( iStat == 0 )
|
if ( iStat == 0 )
|
||||||
{
|
{
|
||||||
qDebug() << "passed";
|
qDebug() << "TestNames passed";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
qDebug() << "\n failed with " << iStat << " errors";
|
qDebug() << "\n TestNames failed with " << iStat << " errors";
|
||||||
}
|
}
|
||||||
|
|
||||||
return iStat;
|
return iStat;
|
||||||
|
@ -398,11 +397,11 @@ int QmuParserTester::TestSyntax()
|
||||||
|
|
||||||
if ( iStat == 0 )
|
if ( iStat == 0 )
|
||||||
{
|
{
|
||||||
qDebug() << "passed";
|
qDebug() << "TestSyntax passed";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
qDebug() << "\n failed with " << iStat << " errors";
|
qDebug() << "\n TestSyntax failed with " << iStat << " errors";
|
||||||
}
|
}
|
||||||
|
|
||||||
return iStat;
|
return iStat;
|
||||||
|
@ -531,11 +530,11 @@ int QmuParserTester::TestVarConst()
|
||||||
|
|
||||||
if ( iStat == 0 )
|
if ( iStat == 0 )
|
||||||
{
|
{
|
||||||
qDebug() << "passed";
|
qDebug() << "TestVarConst passed";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
qDebug() << "\n failed with " << iStat << " errors";
|
qDebug() << "\n TestVarConst failed with " << iStat << " errors";
|
||||||
}
|
}
|
||||||
|
|
||||||
return iStat;
|
return iStat;
|
||||||
|
@ -629,11 +628,11 @@ int QmuParserTester::TestMultiArg()
|
||||||
|
|
||||||
if ( iStat == 0 )
|
if ( iStat == 0 )
|
||||||
{
|
{
|
||||||
qDebug() << "passed";
|
qDebug() << "TestMultiArg passed";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
qDebug() << "\n failed with " << iStat << " errors";
|
qDebug() << "\n TestMultiArg failed with " << iStat << " errors";
|
||||||
}
|
}
|
||||||
|
|
||||||
return iStat;
|
return iStat;
|
||||||
|
@ -698,11 +697,11 @@ int QmuParserTester::TestInfixOprt()
|
||||||
|
|
||||||
if ( iStat == 0 )
|
if ( iStat == 0 )
|
||||||
{
|
{
|
||||||
qDebug() << "passed";
|
qDebug() << "TestInfixOprt passed";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
qDebug() << "\n failed with " << iStat << " errors";
|
qDebug() << "\n TestInfixOprt failed with " << iStat << " errors";
|
||||||
}
|
}
|
||||||
|
|
||||||
return iStat;
|
return iStat;
|
||||||
|
@ -754,11 +753,11 @@ int QmuParserTester::TestPostFix()
|
||||||
|
|
||||||
if ( iStat == 0 )
|
if ( iStat == 0 )
|
||||||
{
|
{
|
||||||
qDebug() << "passed";
|
qDebug() << "TestPostFix passed";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
qDebug() << "\n failed with " << iStat << " errors";
|
qDebug() << "\n TestPostFix failed with " << iStat << " errors";
|
||||||
}
|
}
|
||||||
|
|
||||||
return iStat;
|
return iStat;
|
||||||
|
@ -792,6 +791,8 @@ int QmuParserTester::TestExpression()
|
||||||
|
|
||||||
iStat += EqnTest ( "(2*b+1)*4", ( 2 * b + 1 ) * 4, true );
|
iStat += EqnTest ( "(2*b+1)*4", ( 2 * b + 1 ) * 4, true );
|
||||||
iStat += EqnTest ( "4*(2*b+1)", ( 2 * b + 1 ) * 4, true );
|
iStat += EqnTest ( "4*(2*b+1)", ( 2 * b + 1 ) * 4, true );
|
||||||
|
// 2013-11-27 Issue 2: https://code.google.com/p/muparser/issues/detail?id=2
|
||||||
|
iStat += EqnTest ( "1+2+3", 6, true );
|
||||||
|
|
||||||
// operator precedencs
|
// operator precedencs
|
||||||
iStat += EqnTest ( "1+2-3*4/5^6", 2.99923, true );
|
iStat += EqnTest ( "1+2-3*4/5^6", 2.99923, true );
|
||||||
|
@ -839,11 +840,11 @@ int QmuParserTester::TestExpression()
|
||||||
|
|
||||||
if ( iStat == 0 )
|
if ( iStat == 0 )
|
||||||
{
|
{
|
||||||
qDebug() << "passed";
|
qDebug() << "TestExpression passed";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
qDebug() << "\n failed with " << iStat << " errors";
|
qDebug() << "\n TestExpression failed with " << iStat << " errors";
|
||||||
}
|
}
|
||||||
|
|
||||||
return iStat;
|
return iStat;
|
||||||
|
@ -949,11 +950,11 @@ int QmuParserTester::TestIfThenElse()
|
||||||
|
|
||||||
if ( iStat == 0 )
|
if ( iStat == 0 )
|
||||||
{
|
{
|
||||||
qDebug() << "passed";
|
qDebug() << "TestIfThenElse passed";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
qDebug() << "\n failed with " << iStat << " errors";
|
qDebug() << "\n TestIfThenElse failed with " << iStat << " errors";
|
||||||
}
|
}
|
||||||
|
|
||||||
return iStat;
|
return iStat;
|
||||||
|
@ -1047,11 +1048,11 @@ int QmuParserTester::TestException()
|
||||||
|
|
||||||
if ( iStat == 0 )
|
if ( iStat == 0 )
|
||||||
{
|
{
|
||||||
qDebug() << "passed";
|
qDebug() << "TestException passed";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
qDebug() << "\n failed with " << iStat << " errors";
|
qDebug() << "\n TestException failed with " << iStat << " errors";
|
||||||
}
|
}
|
||||||
|
|
||||||
return iStat;
|
return iStat;
|
||||||
|
@ -1076,7 +1077,7 @@ void QmuParserTester::Run()
|
||||||
iStat += ( this->*m_vTestFun[i] ) ();
|
iStat += ( this->*m_vTestFun[i] ) ();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
catch ( QmuParser::exception_type &e )
|
catch ( QmuParserError &e )
|
||||||
{
|
{
|
||||||
qDebug() << "\n" << e.GetMsg();
|
qDebug() << "\n" << e.GetMsg();
|
||||||
qDebug() << e.GetToken();
|
qDebug() << e.GetToken();
|
||||||
|
@ -1130,14 +1131,12 @@ int QmuParserTester::ThrowTest ( const QString &a_str, int a_iErrc, bool a_bFail
|
||||||
p.SetExpr ( a_str );
|
p.SetExpr ( a_str );
|
||||||
p.Eval();
|
p.Eval();
|
||||||
}
|
}
|
||||||
catch ( QmuParserError &e )
|
catch ( const qmu::QmuParserError &e )
|
||||||
{
|
{
|
||||||
// output the formula in case of an failed test
|
// output the formula in case of an failed test
|
||||||
if ( a_bFail == false || ( a_bFail == true && a_iErrc != e.GetCode() ) )
|
if ( a_bFail == false || ( a_bFail == true && a_iErrc != e.GetCode() ) )
|
||||||
{
|
{
|
||||||
qDebug() << "\n "
|
qDebug() << "\n " << "Expression: " << a_str << " Code:" << e.GetCode() << "(" << e.GetMsg() << ")"
|
||||||
<< "Expression: " << a_str
|
|
||||||
<< " Code:" << e.GetCode() << "(" << e.GetMsg() << ")"
|
|
||||||
<< " Expected:" << a_iErrc;
|
<< " Expected:" << a_iErrc;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1194,7 +1193,7 @@ int QmuParserTester::EqnTestWithVarChange ( const QString &a_str, double a_fVar1
|
||||||
throw std::runtime_error ( "incorrect result (second pass)" );
|
throw std::runtime_error ( "incorrect result (second pass)" );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
catch ( QmuParser::exception_type &e )
|
catch ( QmuParserError &e )
|
||||||
{
|
{
|
||||||
qDebug() << "\n fail: " << a_str << " (" << e.GetMsg() << ")";
|
qDebug() << "\n fail: " << a_str << " (" << e.GetMsg() << ")";
|
||||||
return 1;
|
return 1;
|
||||||
|
@ -1308,7 +1307,7 @@ int QmuParserTester::EqnTest ( const QString &a_str, double a_fRes, bool a_fPass
|
||||||
fVal[1] = p1->Eval(); // result from bytecode
|
fVal[1] = p1->Eval(); // result from bytecode
|
||||||
if ( qFuzzyCompare( fVal[0], fVal[1] ) == false )
|
if ( qFuzzyCompare( fVal[0], fVal[1] ) == false )
|
||||||
{
|
{
|
||||||
throw QmuParser::exception_type ( "Bytecode / string parsing mismatch." );
|
throw QmuParserError ( "Bytecode / string parsing mismatch." );
|
||||||
}
|
}
|
||||||
|
|
||||||
// Test copy and assignement operators
|
// Test copy and assignement operators
|
||||||
|
@ -1379,7 +1378,7 @@ int QmuParserTester::EqnTest ( const QString &a_str, double a_fRes, bool a_fPass
|
||||||
<< fVal[4] << ").";
|
<< fVal[4] << ").";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
catch ( QmuParser::exception_type &e )
|
catch ( QmuParserError &e )
|
||||||
{
|
{
|
||||||
if ( a_fPass )
|
if ( a_fPass )
|
||||||
{
|
{
|
||||||
|
|
|
@ -23,9 +23,7 @@
|
||||||
#ifndef QMUPARSERTEST_H
|
#ifndef QMUPARSERTEST_H
|
||||||
#define QMUPARSERTEST_H
|
#define QMUPARSERTEST_H
|
||||||
|
|
||||||
#include <string>
|
#include "qmuparser_global.h"
|
||||||
#include <cstdlib>
|
|
||||||
#include <numeric> // for accumulate
|
|
||||||
#include "qmuparser.h"
|
#include "qmuparser.h"
|
||||||
#include <QString>
|
#include <QString>
|
||||||
|
|
||||||
|
@ -47,7 +45,7 @@ namespace Test
|
||||||
*
|
*
|
||||||
* (C) 2004-2011 Ingo Berg
|
* (C) 2004-2011 Ingo Berg
|
||||||
*/
|
*/
|
||||||
class QmuParserTester // final
|
class QMUPARSERSHARED_EXPORT QmuParserTester // final
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
typedef int ( QmuParserTester::*testfun_type ) ();
|
typedef int ( QmuParserTester::*testfun_type ) ();
|
||||||
|
@ -186,7 +184,7 @@ private:
|
||||||
{
|
{
|
||||||
if ( a_iArgc == false)
|
if ( a_iArgc == false)
|
||||||
{
|
{
|
||||||
throw qmu::QmuParser::exception_type ( "too few arguments for function FirstArg." );
|
throw QmuParserError ( "too few arguments for function FirstArg." );
|
||||||
}
|
}
|
||||||
|
|
||||||
return a_afArg[0];
|
return a_afArg[0];
|
||||||
|
@ -196,7 +194,7 @@ private:
|
||||||
{
|
{
|
||||||
if ( a_iArgc == false)
|
if ( a_iArgc == false)
|
||||||
{
|
{
|
||||||
throw qmu::QmuParser::exception_type ( "too few arguments for function LastArg." );
|
throw QmuParserError ( "too few arguments for function LastArg." );
|
||||||
}
|
}
|
||||||
|
|
||||||
return a_afArg[a_iArgc - 1];
|
return a_afArg[a_iArgc - 1];
|
||||||
|
@ -206,7 +204,7 @@ private:
|
||||||
{
|
{
|
||||||
if ( a_iArgc == false)
|
if ( a_iArgc == false)
|
||||||
{
|
{
|
||||||
throw qmu::QmuParser::exception_type ( "too few arguments for function sum." );
|
throw QmuParserError ( "too few arguments for function sum." );
|
||||||
}
|
}
|
||||||
|
|
||||||
qreal fRes = 0;
|
qreal fRes = 0;
|
||||||
|
|
|
@ -232,7 +232,7 @@ public:
|
||||||
*
|
*
|
||||||
* In cmSTRFUNC - This is the index to a string table in the main parser.
|
* In cmSTRFUNC - This is the index to a string table in the main parser.
|
||||||
* @param a_iIdx The index the string function result will take in the bytecode parser.
|
* @param a_iIdx The index the string function result will take in the bytecode parser.
|
||||||
* @throw exception_type if #a_iIdx<0 or #m_iType!=cmSTRING
|
* @throw QmuParserError if #a_iIdx<0 or #m_iType!=cmSTRING
|
||||||
*/
|
*/
|
||||||
void SetIdx ( int a_iIdx )
|
void SetIdx ( int a_iIdx )
|
||||||
{
|
{
|
||||||
|
@ -250,7 +250,7 @@ public:
|
||||||
*
|
*
|
||||||
* In cmSTRFUNC - This is the index to a string table in the main parser.
|
* In cmSTRFUNC - This is the index to a string table in the main parser.
|
||||||
*
|
*
|
||||||
* @throw exception_type if #m_iIdx<0 or #m_iType!=cmSTRING
|
* @throw QmuParserError if #m_iIdx<0 or #m_iType!=cmSTRING
|
||||||
* @return The index the result will take in the Bytecode calculatin array (#m_iIdx).
|
* @return The index the result will take in the Bytecode calculatin array (#m_iIdx).
|
||||||
*/
|
*/
|
||||||
int GetIdx() const
|
int GetIdx() const
|
||||||
|
@ -327,7 +327,7 @@ public:
|
||||||
* @brief Return the address of the callback function assoziated with function and operator tokens.
|
* @brief Return the address of the callback function assoziated with function and operator tokens.
|
||||||
*
|
*
|
||||||
* @return The pointer stored in #m_pTok.
|
* @return The pointer stored in #m_pTok.
|
||||||
* @throw exception_type if token type is non of:
|
* @throw QmuParserError if token type is non of:
|
||||||
* <ul>
|
* <ul>
|
||||||
* <li>cmFUNC</li>
|
* <li>cmFUNC</li>
|
||||||
* <li>cmSTRFUNC</li>
|
* <li>cmSTRFUNC</li>
|
||||||
|
@ -348,7 +348,7 @@ public:
|
||||||
* @brief Get value of the token.
|
* @brief Get value of the token.
|
||||||
*
|
*
|
||||||
* Only applicable to variable and value tokens.
|
* Only applicable to variable and value tokens.
|
||||||
* @throw exception_type if token is no value/variable token.
|
* @throw QmuParserError if token is no value/variable token.
|
||||||
*/
|
*/
|
||||||
TBase GetVal() const
|
TBase GetVal() const
|
||||||
{
|
{
|
||||||
|
@ -359,107 +359,39 @@ public:
|
||||||
case cmVAR:
|
case cmVAR:
|
||||||
return * ( reinterpret_cast<TBase*>(m_pTok) );
|
return * ( reinterpret_cast<TBase*>(m_pTok) );
|
||||||
case cmLE:
|
case cmLE:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmGE:
|
case cmGE:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmNEQ:
|
case cmNEQ:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmEQ:
|
case cmEQ:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmLT:
|
case cmLT:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmGT:
|
case cmGT:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmADD:
|
case cmADD:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmSUB:
|
case cmSUB:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmMUL:
|
case cmMUL:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmDIV:
|
case cmDIV:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmPOW:
|
case cmPOW:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmLAND:
|
case cmLAND:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmLOR:
|
case cmLOR:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmASSIGN:
|
case cmASSIGN:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmBO:
|
case cmBO:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmBC:
|
case cmBC:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmIF:
|
case cmIF:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmELSE:
|
case cmELSE:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmENDIF:
|
case cmENDIF:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmARG_SEP:
|
case cmARG_SEP:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmVARPOW2:
|
case cmVARPOW2:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmVARPOW3:
|
case cmVARPOW3:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmVARPOW4:
|
case cmVARPOW4:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmVARMUL:
|
case cmVARMUL:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmPOW2:
|
case cmPOW2:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmFUNC:
|
case cmFUNC:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmFUNC_STR:
|
case cmFUNC_STR:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmFUNC_BULK:
|
case cmFUNC_BULK:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmSTRING:
|
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmOPRT_BIN:
|
case cmOPRT_BIN:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmOPRT_POSTFIX:
|
case cmOPRT_POSTFIX:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmOPRT_INFIX:
|
case cmOPRT_INFIX:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmEND:
|
case cmEND:
|
||||||
Q_UNREACHABLE();
|
|
||||||
break;
|
|
||||||
case cmUNKNOWN:
|
case cmUNKNOWN:
|
||||||
Q_UNREACHABLE();
|
case cmSTRING:
|
||||||
break;
|
|
||||||
default:
|
default:
|
||||||
throw QmuParserError ( ecVAL_EXPECTED );
|
throw QmuParserError ( ecVAL_EXPECTED );
|
||||||
}
|
}
|
||||||
|
@ -470,7 +402,7 @@ public:
|
||||||
* @brief Get address of a variable token.
|
* @brief Get address of a variable token.
|
||||||
*
|
*
|
||||||
* Valid only if m_iType==CmdVar.
|
* Valid only if m_iType==CmdVar.
|
||||||
* @throw exception_type if token is no variable token.
|
* @throw QmuParserError if token is no variable token.
|
||||||
*/
|
*/
|
||||||
TBase* GetVar() const
|
TBase* GetVar() const
|
||||||
{
|
{
|
||||||
|
|
|
@ -254,15 +254,10 @@ QmuParserTokenReader::token_type QmuParserTokenReader::ReadNextToken()
|
||||||
{
|
{
|
||||||
assert ( m_pParser );
|
assert ( m_pParser );
|
||||||
|
|
||||||
#if defined(_UNICODE)
|
|
||||||
const char_type *szFormula = m_strFormula.toStdWString().c_str();
|
|
||||||
#else
|
|
||||||
const char_type *szFormula = m_strFormula.toStdString().c_str();
|
|
||||||
#endif
|
|
||||||
token_type tok;
|
token_type tok;
|
||||||
|
|
||||||
// Ignore all non printable characters when reading the expression
|
// Ignore all non printable characters when reading the expression
|
||||||
while ( szFormula[m_iPos] > 0 && szFormula[m_iPos] <= 0x20 )
|
while ( m_strFormula.data()[m_iPos] > 0 && m_strFormula.data()[m_iPos] <= 0x20 )
|
||||||
{
|
{
|
||||||
++m_iPos;
|
++m_iPos;
|
||||||
}
|
}
|
||||||
|
@ -452,7 +447,7 @@ bool QmuParserTokenReader::IsBuiltIn ( token_type &a_Tok )
|
||||||
for ( int i = 0; i < pOprtDef.size(); ++i )
|
for ( int i = 0; i < pOprtDef.size(); ++i )
|
||||||
{
|
{
|
||||||
int len = pOprtDef.at ( i ).length();
|
int len = pOprtDef.at ( i ).length();
|
||||||
if ( pOprtDef.at ( i ) == m_strFormula.mid ( m_iPos, m_iPos + len ) )
|
if ( pOprtDef.at ( i ) == m_strFormula.mid ( m_iPos, len ) )
|
||||||
{
|
{
|
||||||
switch ( i )
|
switch ( i )
|
||||||
{
|
{
|
||||||
|
@ -596,23 +591,31 @@ bool QmuParserTokenReader::IsArgSep ( token_type &a_Tok )
|
||||||
*
|
*
|
||||||
* @return true if an end of formula is found false otherwise.
|
* @return true if an end of formula is found false otherwise.
|
||||||
* @param a_Tok [out] If an eof is found the corresponding token will be stored there.
|
* @param a_Tok [out] If an eof is found the corresponding token will be stored there.
|
||||||
* @throw nothrow
|
|
||||||
* @sa IsOprt, IsFunTok, IsStrFunTok, IsValTok, IsVarTok, IsString, IsInfixOpTok, IsPostOpTok
|
* @sa IsOprt, IsFunTok, IsStrFunTok, IsValTok, IsVarTok, IsString, IsInfixOpTok, IsPostOpTok
|
||||||
*/
|
*/
|
||||||
bool QmuParserTokenReader::IsEOF ( token_type &a_Tok ) Q_DECL_NOEXCEPT
|
bool QmuParserTokenReader::IsEOF ( token_type &a_Tok )
|
||||||
{
|
{
|
||||||
#if defined(_UNICODE)
|
//#if defined(_UNICODE)
|
||||||
const char_type* szFormula = m_strFormula.toStdWString().c_str();
|
// const char_type* szFormula = m_strFormula.toStdWString().c_str();
|
||||||
#else
|
//#else
|
||||||
const char_type* szFormula = m_strFormula.toStdString().c_str();
|
// const char_type* szFormula = m_strFormula.toStdString().c_str();
|
||||||
#endif
|
//#endif
|
||||||
|
|
||||||
// check for EOF
|
// check for EOF
|
||||||
if ( szFormula[m_iPos] == false /*|| szFormula[m_iPos] == '\n'*/ )
|
if ( m_strFormula.data()[m_iPos] == false /*|| szFormula[m_iPos] == '\n'*/ )
|
||||||
{
|
{
|
||||||
if ( m_iSynFlags & noEND )
|
if ( m_iSynFlags & noEND )
|
||||||
{
|
{
|
||||||
Error ( ecUNEXPECTED_EOF, m_iPos );
|
try
|
||||||
|
{
|
||||||
|
Error ( ecUNEXPECTED_EOF, m_iPos );
|
||||||
|
}
|
||||||
|
catch (qmu::QmuParserError &e)
|
||||||
|
{
|
||||||
|
qDebug() << "\n "
|
||||||
|
<< " Code:" << e.GetCode() << "(" << e.GetMsg() << ")";
|
||||||
|
throw e;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( m_iBrackets > 0 )
|
if ( m_iBrackets > 0 )
|
||||||
|
@ -756,7 +759,7 @@ bool QmuParserTokenReader::IsOprt ( token_type &a_Tok )
|
||||||
for ( ; it != m_pOprtDef->rend(); ++it )
|
for ( ; it != m_pOprtDef->rend(); ++it )
|
||||||
{
|
{
|
||||||
const QString &sID = it->first;
|
const QString &sID = it->first;
|
||||||
if ( sID == m_strFormula.mid ( m_iPos, m_iPos + sID.length() ) )
|
if ( sID == m_strFormula.mid ( m_iPos, sID.length() ) )
|
||||||
{
|
{
|
||||||
a_Tok.Set ( it->second, strTok );
|
a_Tok.Set ( it->second, strTok );
|
||||||
|
|
||||||
|
@ -891,7 +894,8 @@ bool QmuParserTokenReader::IsValTok ( token_type &a_Tok )
|
||||||
if ( ( *item ) ( m_strFormula.mid ( m_iPos ), &m_iPos, &fVal ) == 1 )
|
if ( ( *item ) ( m_strFormula.mid ( m_iPos ), &m_iPos, &fVal ) == 1 )
|
||||||
{
|
{
|
||||||
// 2013-11-27 Issue 2: https://code.google.com/p/muparser/issues/detail?id=2
|
// 2013-11-27 Issue 2: https://code.google.com/p/muparser/issues/detail?id=2
|
||||||
strTok = m_strFormula.mid ( iStart, m_iPos-iStart );
|
//strTok = m_strFormula.mid ( iStart, m_iPos-iStart );
|
||||||
|
strTok = m_strFormula.mid ( iStart, m_iPos );
|
||||||
if ( m_iSynFlags & noVAL )
|
if ( m_iSynFlags & noVAL )
|
||||||
{
|
{
|
||||||
Error ( ecUNEXPECTED_VAL, m_iPos - strTok.length(), strTok );
|
Error ( ecUNEXPECTED_VAL, m_iPos - strTok.length(), strTok );
|
||||||
|
@ -1050,16 +1054,15 @@ bool QmuParserTokenReader::IsUndefVarTok ( token_type &a_Tok ) Q_DECL_NOEXCEPT
|
||||||
* @param a_Tok [out] If a variable token has been found it will be placed here.
|
* @param a_Tok [out] If a variable token has been found it will be placed here.
|
||||||
* @return true if a string token has been found.
|
* @return true if a string token has been found.
|
||||||
* @sa IsOprt, IsFunTok, IsStrFunTok, IsValTok, IsVarTok, IsEOF, IsInfixOpTok, IsPostOpTok
|
* @sa IsOprt, IsFunTok, IsStrFunTok, IsValTok, IsVarTok, IsEOF, IsInfixOpTok, IsPostOpTok
|
||||||
* @throw nothrow
|
|
||||||
*/
|
*/
|
||||||
bool QmuParserTokenReader::IsString ( token_type &a_Tok ) Q_DECL_NOEXCEPT
|
bool QmuParserTokenReader::IsString ( token_type &a_Tok )
|
||||||
{
|
{
|
||||||
if ( m_strFormula[m_iPos] != '"' )
|
if ( m_strFormula[m_iPos] != '"' )
|
||||||
{
|
{
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
QString strBuf ( m_strFormula[m_iPos + 1] );
|
QString strBuf (m_strFormula.mid(m_iPos + 1));
|
||||||
int iEnd ( 0 ), iSkip ( 0 );
|
int iEnd ( 0 ), iSkip ( 0 );
|
||||||
|
|
||||||
// parser over escaped '\"' end replace them with '"'
|
// parser over escaped '\"' end replace them with '"'
|
||||||
|
@ -1105,7 +1108,7 @@ bool QmuParserTokenReader::IsString ( token_type &a_Tok ) Q_DECL_NOEXCEPT
|
||||||
* @param a_strTok [in] The token string representation associated with the error.
|
* @param a_strTok [in] The token string representation associated with the error.
|
||||||
* @throw ParserException always throws thats the only purpose of this function.
|
* @throw ParserException always throws thats the only purpose of this function.
|
||||||
*/
|
*/
|
||||||
void QmuParserTokenReader::Error ( EErrorCodes a_iErrc, int a_iPos, const QString &a_sTok ) const
|
void Q_NORETURN QmuParserTokenReader::Error ( EErrorCodes a_iErrc, int a_iPos, const QString &a_sTok ) const
|
||||||
{
|
{
|
||||||
m_pParser->Error ( a_iErrc, a_iPos, a_sTok );
|
m_pParser->Error ( a_iErrc, a_iPos, a_sTok );
|
||||||
}
|
}
|
||||||
|
|
|
@ -23,66 +23,53 @@
|
||||||
#ifndef QMUPARSERTOKENREADER_H
|
#ifndef QMUPARSERTOKENREADER_H
|
||||||
#define QMUPARSERTOKENREADER_H
|
#define QMUPARSERTOKENREADER_H
|
||||||
|
|
||||||
#include <cassert>
|
|
||||||
#include <cstdio>
|
|
||||||
#include <cstring>
|
|
||||||
#include <list>
|
|
||||||
#include <map>
|
|
||||||
#include <memory>
|
|
||||||
#include <stack>
|
|
||||||
#include <string>
|
|
||||||
|
|
||||||
#include "qmuparserdef.h"
|
#include "qmuparserdef.h"
|
||||||
#include "qmuparsertoken.h"
|
#include "qmuparsertoken.h"
|
||||||
|
|
||||||
/** @file
|
/**
|
||||||
@brief This file contains the parser token reader definition.
|
* @file
|
||||||
*/
|
* @brief This file contains the parser token reader definition.
|
||||||
|
*/
|
||||||
|
|
||||||
namespace qmu
|
namespace qmu
|
||||||
{
|
{
|
||||||
// Forward declaration
|
// Forward declaration
|
||||||
class QmuParserBase;
|
class QmuParserBase;
|
||||||
|
|
||||||
/** @brief Token reader for the ParserBase class.
|
/**
|
||||||
|
* @brief Token reader for the ParserBase class.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
class QmuParserTokenReader
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
typedef QmuParserToken<qreal, QString> token_type;
|
||||||
|
public:
|
||||||
|
QmuParserTokenReader(QmuParserBase *a_pParent);
|
||||||
|
QmuParserTokenReader* Clone(QmuParserBase *a_pParent) const Q_DECL_NOEXCEPT;
|
||||||
|
|
||||||
*/
|
void AddValIdent(identfun_type a_pCallback);
|
||||||
class QmuParserTokenReader
|
void SetVarCreator(facfun_type a_pFactory, void *pUserData);
|
||||||
{
|
void SetFormula(const QString &a_strFormula);
|
||||||
private:
|
void SetArgSep(char_type cArgSep);
|
||||||
|
int GetPos() const Q_DECL_NOEXCEPT;
|
||||||
|
const QString& GetExpr() const Q_DECL_NOEXCEPT;
|
||||||
|
varmap_type& GetUsedVar();
|
||||||
|
QChar GetArgSep() const;
|
||||||
|
void IgnoreUndefVar(bool bIgnore);
|
||||||
|
void ReInit() Q_DECL_NOEXCEPT;
|
||||||
|
token_type ReadNextToken();
|
||||||
|
private:
|
||||||
|
|
||||||
typedef QmuParserToken<qreal, QString> token_type;
|
/**
|
||||||
|
* @brief Syntax codes.
|
||||||
public:
|
*
|
||||||
|
* The syntax codes control the syntax check done during the first time parsing of
|
||||||
QmuParserTokenReader(QmuParserBase *a_pParent);
|
* the expression string. They are flags that indicate which tokens are allowed next
|
||||||
QmuParserTokenReader* Clone(QmuParserBase *a_pParent) const Q_DECL_NOEXCEPT;
|
* if certain tokens are identified.
|
||||||
|
*/
|
||||||
void AddValIdent(identfun_type a_pCallback);
|
enum ESynCodes
|
||||||
void SetVarCreator(facfun_type a_pFactory, void *pUserData);
|
{
|
||||||
void SetFormula(const QString &a_strFormula);
|
|
||||||
void SetArgSep(char_type cArgSep);
|
|
||||||
|
|
||||||
int GetPos() const Q_DECL_NOEXCEPT;
|
|
||||||
const QString &GetExpr() const Q_DECL_NOEXCEPT;
|
|
||||||
varmap_type& GetUsedVar();
|
|
||||||
QChar GetArgSep() const;
|
|
||||||
|
|
||||||
void IgnoreUndefVar(bool bIgnore);
|
|
||||||
void ReInit() Q_DECL_NOEXCEPT;
|
|
||||||
token_type ReadNextToken();
|
|
||||||
|
|
||||||
private:
|
|
||||||
/**
|
|
||||||
* @brief Syntax codes.
|
|
||||||
*
|
|
||||||
* The syntax codes control the syntax check done during the first time parsing of
|
|
||||||
* the expression string. They are flags that indicate which tokens are allowed next
|
|
||||||
* if certain tokens are identified.
|
|
||||||
*/
|
|
||||||
enum ESynCodes
|
|
||||||
{
|
|
||||||
noBO = 1 << 0, ///< to avoid i.e. "cos(7)("
|
noBO = 1 << 0, ///< to avoid i.e. "cos(7)("
|
||||||
noBC = 1 << 1, ///< to avoid i.e. "sin)" or "()"
|
noBC = 1 << 1, ///< to avoid i.e. "sin)" or "()"
|
||||||
noVAL = 1 << 2, ///< to avoid i.e. "tan 2" or "sin(8)3.14"
|
noVAL = 1 << 2, ///< to avoid i.e. "tan 2" or "sin(8)3.14"
|
||||||
|
@ -99,56 +86,54 @@ namespace qmu
|
||||||
noELSE = 1 << 13,
|
noELSE = 1 << 13,
|
||||||
sfSTART_OF_LINE = noOPT | noBC | noPOSTOP | noASSIGN | noIF | noELSE | noARG_SEP,
|
sfSTART_OF_LINE = noOPT | noBC | noPOSTOP | noASSIGN | noIF | noELSE | noARG_SEP,
|
||||||
noANY = ~0 ///< All of he above flags set
|
noANY = ~0 ///< All of he above flags set
|
||||||
};
|
};
|
||||||
|
|
||||||
QmuParserTokenReader(const QmuParserTokenReader &a_Reader);
|
QmuParserTokenReader(const QmuParserTokenReader &a_Reader);
|
||||||
QmuParserTokenReader& operator=(const QmuParserTokenReader &a_Reader) Q_DECL_NOEXCEPT;
|
QmuParserTokenReader& operator=(const QmuParserTokenReader &a_Reader) Q_DECL_NOEXCEPT;
|
||||||
void Assign(const QmuParserTokenReader &a_Reader) Q_DECL_NOEXCEPT;
|
void Assign(const QmuParserTokenReader &a_Reader) Q_DECL_NOEXCEPT;
|
||||||
|
|
||||||
void SetParent(QmuParserBase *a_pParent);
|
void SetParent(QmuParserBase *a_pParent);
|
||||||
int ExtractToken(const QString &a_szCharSet, QString &a_strTok, int a_iPos) const Q_DECL_NOEXCEPT;
|
int ExtractToken(const QString &a_szCharSet, QString &a_strTok, int a_iPos) const Q_DECL_NOEXCEPT;
|
||||||
int ExtractOperatorToken(QString &a_sTok, int a_iPos) const;
|
int ExtractOperatorToken(QString &a_sTok, int a_iPos) const;
|
||||||
|
|
||||||
bool IsBuiltIn(token_type &a_Tok);
|
bool IsBuiltIn(token_type &a_Tok);
|
||||||
bool IsArgSep(token_type &a_Tok);
|
bool IsArgSep(token_type &a_Tok);
|
||||||
bool IsEOF(token_type &a_Tok) Q_DECL_NOEXCEPT;
|
bool IsEOF(token_type &a_Tok);
|
||||||
bool IsInfixOpTok(token_type &a_Tok);
|
bool IsInfixOpTok(token_type &a_Tok);
|
||||||
bool IsFunTok(token_type &a_Tok);
|
bool IsFunTok(token_type &a_Tok);
|
||||||
bool IsPostOpTok(token_type &a_Tok);
|
bool IsPostOpTok(token_type &a_Tok);
|
||||||
bool IsOprt(token_type &a_Tok);
|
bool IsOprt(token_type &a_Tok);
|
||||||
bool IsValTok(token_type &a_Tok);
|
bool IsValTok(token_type &a_Tok);
|
||||||
bool IsVarTok(token_type &a_Tok);
|
bool IsVarTok(token_type &a_Tok);
|
||||||
bool IsStrVarTok(token_type &a_Tok);
|
bool IsStrVarTok(token_type &a_Tok);
|
||||||
bool IsUndefVarTok(token_type &a_Tok) Q_DECL_NOEXCEPT;
|
bool IsUndefVarTok(token_type &a_Tok) Q_DECL_NOEXCEPT;
|
||||||
bool IsString(token_type &a_Tok) Q_DECL_NOEXCEPT;
|
bool IsString(token_type &a_Tok);
|
||||||
void Error(EErrorCodes a_iErrc,
|
void Q_NORETURN Error(EErrorCodes a_iErrc, int a_iPos = -1, const QString &a_sTok = QString() ) const;
|
||||||
int a_iPos = -1,
|
|
||||||
const QString &a_sTok = QString() ) const;
|
|
||||||
|
|
||||||
token_type& SaveBeforeReturn(const token_type &tok);
|
token_type& SaveBeforeReturn(const token_type &tok);
|
||||||
|
|
||||||
QmuParserBase *m_pParser;
|
QmuParserBase *m_pParser;
|
||||||
QString m_strFormula;
|
QString m_strFormula;
|
||||||
int m_iPos;
|
int m_iPos;
|
||||||
int m_iSynFlags;
|
int m_iSynFlags;
|
||||||
bool m_bIgnoreUndefVar;
|
bool m_bIgnoreUndefVar;
|
||||||
|
|
||||||
const funmap_type *m_pFunDef;
|
const funmap_type *m_pFunDef;
|
||||||
const funmap_type *m_pPostOprtDef;
|
const funmap_type *m_pPostOprtDef;
|
||||||
const funmap_type *m_pInfixOprtDef;
|
const funmap_type *m_pInfixOprtDef;
|
||||||
const funmap_type *m_pOprtDef;
|
const funmap_type *m_pOprtDef;
|
||||||
const valmap_type *m_pConstDef;
|
const valmap_type *m_pConstDef;
|
||||||
const strmap_type *m_pStrVarDef;
|
const strmap_type *m_pStrVarDef;
|
||||||
varmap_type *m_pVarDef; ///< The only non const pointer to parser internals
|
varmap_type *m_pVarDef; ///< The only non const pointer to parser internals
|
||||||
facfun_type m_pFactory;
|
facfun_type m_pFactory;
|
||||||
void *m_pFactoryData;
|
void *m_pFactoryData;
|
||||||
std::list<identfun_type> m_vIdentFun; ///< Value token identification function
|
std::list<identfun_type> m_vIdentFun; ///< Value token identification function
|
||||||
varmap_type m_UsedVar;
|
varmap_type m_UsedVar;
|
||||||
qreal m_fZero; ///< Dummy value of zero, referenced by undefined variables
|
qreal m_fZero; ///< Dummy value of zero, referenced by undefined variables
|
||||||
int m_iBrackets;
|
int m_iBrackets; ///< Keep count open brackets
|
||||||
token_type m_lastTok;
|
token_type m_lastTok;
|
||||||
QChar m_cArgSep; ///< The character used for separating function arguments
|
QChar m_cArgSep; ///< The character used for separating function arguments
|
||||||
};
|
};
|
||||||
} // namespace qmu
|
} // namespace qmu
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
Loading…
Reference in New Issue
Block a user