2016-02-26 2 views
1

Здравствуйте, я пытаюсь отправить объект mat на другой компьютер с помощью zeromq и boost.Отправка сериализованного объекта Mat на другой компьютер с использованием zeromq в C++

это мой serialization.h файл

#include <iostream> 
#include <fstream> 
#include <boost/archive/binary_oarchive.hpp> 
#include <boost/archive/binary_iarchive.hpp> 
#include <boost/serialization/split_free.hpp> 
#include <boost/serialization/vector.hpp> 

BOOST_SERIALIZATION_SPLIT_FREE(cv::Mat) 
namespace boost { 
    namespace serialization { 

     /*** Mat ***/ 
     template<class Archive> 
     void save(Archive & ar, const cv::Mat& m, const unsigned int version) 
     { 
      size_t elemSize = m.elemSize(), elemType = m.type(); 

      ar & m.cols; 
      ar & m.rows; 
      ar & elemSize; 
      ar & elemType; // element type. 
      size_t dataSize = m.cols * m.rows * m.elemSize(); 


      for (size_t dc = 0; dc < dataSize; ++dc) { 
       ar & m.data[dc]; 
      } 
     } 

     template<class Archive> 
     void load(Archive & ar, cv::Mat& m, const unsigned int version) 
     { 
      int cols, rows; 
      size_t elemSize, elemType; 

      ar & cols; 
      ar & rows; 
      ar & elemSize; 
      ar & elemType; 

      m.create(rows, cols, elemType); 
      size_t dataSize = m.cols * m.rows * elemSize; 

      //cout << "reading matrix data rows, cols, elemSize, type, datasize: (" << m.rows << "," << m.cols << "," << m.elemSize() << "," << m.type() << "," << dataSize << ")" << endl; 

      for (size_t dc = 0; dc < dataSize; ++dc) { 
       ar & m.data[dc]; 
      } 
     } 

    } 
} 

это как сериализовать мой объект Mat и отправить его.

#include <zmq.hpp> 
#include <string> 
#include <iostream> 
#include "opencv2/highgui/highgui.hpp" 
#include "opencv2/imgproc/imgproc.hpp" 
#include <iostream> 
#include <stdio.h> 
#include <boost/archive/binary_oarchive.hpp> 
#include <boost/archive/binary_iarchive.hpp> 
#include <fstream> 
#include "Serialization.h" 
#include <boost/archive/text_oarchive.hpp> 
#include <boost/archive/text_iarchive.hpp> 

using namespace std; 
using namespace cv; 


std::string save(const cv::Mat & mat) 
{ 
    std::ostringstream oss; 
    boost::archive::text_oarchive toa(oss); 
    toa << mat; 

    return oss.str(); 
} 



int main() { 
    Mat img = imread("/Users/Rodrane/Downloads/barbara.pgm", 0); // Read the file 


    std::string serialized = save(img); 


    // Prepare our context and socket 
    zmq::context_t context (1); 
    zmq::socket_t socket (context, ZMQ_REQ); 

    std::cout << "Connecting to hello world server…" << std::endl; 
    socket.connect ("tcp://localhost:5555"); 

    // Do 10 requests, waiting each time for a response 
    for (int request_nbr = 0; request_nbr != 10; request_nbr++) { 
     zmq::message_t request (sizeof(serialized)); 
     memcpy (request.data(), &serialized, sizeof(serialized)); 
     std::cout << "Sending Hello " << request_nbr << "…" << std::endl; 
     socket.send (request); 

     // Get the reply. 
     zmq::message_t reply; 
     socket.recv (&reply); 
     std::cout << "Received World " << request_nbr << std::endl; 
    } 
    return 0; 



} 

И вот как я получаю свой сериализованный объект и пытаюсь его показать.

#include <zmq.hpp> 
#include <string> 
#include <iostream> 
#include "opencv2/highgui/highgui.hpp" 
#include "opencv2/imgproc/imgproc.hpp" 
#include <iostream> 
#include <stdio.h> 
#include <boost/archive/binary_oarchive.hpp> 
#include <boost/archive/binary_iarchive.hpp> 
#include <fstream> 
#include "Serialization.h" 
#include <boost/archive/text_oarchive.hpp> 
#include <boost/archive/text_iarchive.hpp> 

using namespace std; 

void load(cv::Mat & mat, const char * data_str) 
{ 
    std::stringstream ss; 
    ss << data_str; 

    boost::archive::text_iarchive tia(ss); 
    tia >> mat; 
} 

int main() { 
    zmq::context_t context (1); 
    zmq::socket_t socket (context, ZMQ_REP); 
    socket.bind ("tcp://*:5555"); 
    cv::Mat object; 

    while (true) { 
     zmq::message_t recivedData; 
     socket.recv (&recivedData); 
     std::string rpl = std::string(static_cast<char*>(recivedData.data()), recivedData.size()); 
     const char *cstr = rpl.c_str(); 
     load(object,cstr); 
     imshow("asdasd",object); 
     // Send reply back to client 
     zmq::message_t reply (8); 
     memcpy (reply.data(), "Recieved", 8); 
     socket.send (reply); 
    } 



} 

Когда я запускаю этот 2 проектов я получить ошибку, которая

LibC++ abi.dylib: оканчивающиеся неперехваченного исключением типа zmq :: error_t: Прерванный системный вызов

Поскольку это происходит во время запуска моего проекта клиента, я предполагаю, что сервер получает данные, но либо поврежден, либо возникает проблема с де-сериализацией его

ответ

2

я не пошел через весь код, но это 100% неправильно:

std::string serialized = save(img); 
// ... 
zmq::message_t request (sizeof(serialized)); 
memcpy (request.data(), &serialized, sizeof(serialized)); 

sizeof(std::string) не имеет ничего общего с размером строки Held, и вы не можете тетсру от std::string объекта. Что вы хотите сделать, это:

zmq::message_t request (serialized.length()); 
memcpy (request.data(), serialized.c_str(), serialized.length()); 

Может быть и другие ошибки, но это просто торчит.

+0

это действительно решена моя проблема большое спасибо! –