mercredi 18 janvier 2017

How to successfully decouple these classes

I wasn't sure of the best name for this thread, but I'm trying to refactor some code and remove some decoupling. I am forced to use Visual Studio 2005 C++ without boost, don't ask... (So not c++11, or newer)

I have a protocol that receives messages, and the protocol contains a parser and processor. Parser extracts the information out of the message, and populates a structure. The structure is then passed into the processor to take further action on it.

class Protocol
{
    Parser parser;
    Processor processor;

public:
    Protocol() : parser(processor)
    {

    }

    handleMessage(Message& message)
    {
        ParsedData parsedData;
        parser.parse(message, parsedData);
    }
}

class Parser
{
    Processor processor;

public:
    Parser()
    {

    }

    Parser(Processor& p) : processor(p)
    {
    }

    parse(Message& message, ParsedData& parsedData)
    {
        if(message.type == "whatever")
        {
            parseLevel2(message.message, parsedData);
        }
        //else if Other message types
    }

    parseLevel2(MessageLevel2& message, ParsedData& parsedData)
    {
        //Keep going down the rabbit hole, but for simplicity it ends here
        parsedData.blah = "some data";
        processor.ProcessBlahMessage(parsedData);
    }
}

class Processor
{
public:
    Processor()
    {
    }

    ProcessBlahMessage(ParsedData& parsedData)
    {
        //Do logic
    }
}

I was hoping to strip the Processor from the Parser so it became more like this...

class Protocol
{
    Parser parser;
    Processor processor;

public:
    Protocol() : parser(processor)
    {

    }

    handleMessage(Message& message)
    {
        ParsedData parsedData;
        parser.parse(message, parsedData); //This will not call
        processor.process(parsedData);  //This is the new 

    }
}

The only issue that is preventing me from doing this is I will have to have a bunch of if statements in the process method.

process(ParsedData& parsedData)
{
    if(parsedData.type == "blah")
    {
        ProcessBlahMessage()
    }
    else if(parsedData.type == "grah")
    {
        ProcessGrahMessage()
    }
    //etc...
}

My question is how do I avoid all those if statements where I'm essentially just parsing it again? If I give the parsedData a function pointer, or lambda then I'm still going to need a reference to the processor in the parser.

Aucun commentaire:

Enregistrer un commentaire