从反序列化消息队列中的多个结构时,如何避免“boost :: archive :: archive_exception”?

时间:2014-07-16 14:20:17

标签: c++ boost deserialization

我正在使用Boost.Serialization (v1.46)阅读邮件队列。只要队列只包含一个元素,一切正常。但是当我读取包含多个元素的队列时,抛出以下异常:

terminate called after throwing an instance of 'boost::archive::archive_exception'
what():  invalid signature

archive_exception.hppinvalid signature // first line of archive does not contain expected string"

我正在序列化和反序列化的类看起来如下:

#define MAX_SIZE 1000

class IpcMsg {

public:
    IpcMsg(int logLevel = 0, std::string logMsg = "") :
            logLevel(logLevel), logMsg(logMsg) {
    }
    ;

    int logLevel;
    std::string logMsg;

private:
    friend class boost::serialization::access;

    template<class Archive>
    void serialize(Archive & ar, const unsigned int version) {
        ar & logLevel;
        ar & logMsg;
    }
};

序列化:

try
    {
        message_queue mq
            (
             open_or_create,
             "mq",
             100,
             MAX_SIZE
            );

        IpcMsg logMsg(1, "Test");

        std::stringstream oss;

        boost::archive::text_oarchive oa(oss);
        oa << logMsg;

        std::string serialized_string(oss.str());
        mq.send(serialized_string.data(), serialized_string.size(), 0);
    }
    catch(interprocess_exception &ex)
    {
        std::cerr << ex.what() << std::endl;
    }

反串行化:

...
IpcMsg logEntry;

std::stringstream iss;
std::string serialized_string;
serialized_string.resize(MAX_SIZE);

while(mq.try_receive(&serialized_string[0], MAX_SIZE, recvd_size, priority)){

    iss << serialized_string;

    boost::archive::text_iarchive ia(iss);
    ia >> logEntry;

     msgs.push_back(logEntry);

     std::cout << logEntry.logLevel << std::endl;
     std::cout << logEntry.logMsg << std::endl;
}

1 个答案:

答案 0 :(得分:1)

此代码会创建一个std::stringstream,其中包含最多MAX_SIZE个空字符的消息。

serialized_string.resize(MAX_SIZE);
mq.try_receive(&serialized_string[0], MAX_SIZE, recvd_size, priority);
iss << serialized_string;

我猜测Boost.Serialization正在点击第一条消息之后的NULL字符并错误输出。

也许你可以试试这样的东西?

serialized_string.resize(MAX_SIZE);
mq.try_receive(&serialized_string[0], MAX_SIZE, recvd_size, priority);
serialized_string.resize(recvd_size);
iss << serialized_string;

(另外,我个人并不喜欢像&serialized_string[0]这样的代码。请参阅hereherevector<char>或指向普通老年人的智能指针char[]可能会更好。)