31590


正月明けにすみません。  
"<https://stackoverflow.com/questions/33513051/structures-and-vectors-in-
boost-shared-memory>"という質問にある  
"<http://coliru.stacked-crooked.com/a/0ab21481b69d87bb>" にあるコードを書き換えて  
コードを書いています。  
しかしながら、私はc++の経験はおろか、プログラミングが全くできない関係もあり、

[code]

    data.push_back(id);   // 14 line in main function 
    
[/code]

auto&型のdataという変数でマッチングしないというコンパイルエラーが出てきてしまいました。

[code]

    auto& data = Shared::locate(smt);   // 10 line in "while(1)" of main function
    
[/code]

呼び出し元は上記のところです。

正直言ってコンパイルエラーにだけならないように書き換えてきたので、エラーはここだけではないと思います。  
そういうことなので全てのコードを掲載させていただきます。

どうかお助力のほうをお願いいたします。  
（最終的に共有メモリ内のvectorにミリ秒とOpenCVのMatのuchar*変換とmemcpyのコピー用サイズを格納して子プロセスで一括で取りたいがために書いたコードです。）

[code]

    //  opencv's lib    
    #include <cv.h>
    #include <cxcore.h>
    #include <highgui.h>
    //  opencv's lib end
    #include <string>
    #include <boost/interprocess/managed_shared_memory.hpp>
    
    #include <boost/interprocess/managed_mapped_file.hpp> // use for Coliru
    #include <boost/interprocess/containers/vector.hpp>   // boost/containers/vector.hpp
    #include <boost/interprocess/containers/string.hpp>   // boost/containers/string.hpp
    #include <iostream>
    #include <sys/time.h>
    #include <stdio.h>
    
     //                                                                    void_allocator;
    namespace bip = boost::interprocess;
    
    typedef unsigned char uchar;
    //Typedefs of allocators and containers
    typedef bip::managed_shared_memory::segment_manager                       segment_manager_t;
    typedef bip::allocator<void, segment_manager_t>  void_allocator;
    
    typedef void_allocator::rebind<uchar>::other                           uchar_allocator;
    typedef bip::vector<uchar, uchar_allocator>                                   uchar_vector;
    
    
    
    template <typename Alloc = std::allocator<char> >
    struct BasicInData {
    
        public:
            BasicInData(Alloc alloc = {}) : image(alloc)
            { }
    
            template <typename T>
            BasicInData(double x, int sizeImg, uchar_vector& image, Alloc alloc = {}) :
                x(x), sizeImg(sizeImg), image(alloc)
            { }
    
            double x = 0;
            int sizeImg = 0;
            uchar_vector image;
    };
    
    using InData = BasicInData<>; // just heap allocated
    
    namespace Shared {
        using segment                      = bip::managed_shared_memory;
        using segment_manager              = segment::segment_manager;
    
        template <typename T> using alloc  = bip::allocator<T, segment_manager>;
        template <typename T> using vector = bip::vector<T, alloc<T> >;
    
        using InData = BasicInData<alloc<char> >; // shared memory version
    
        vector<InData>& locate(segment& smt) {
            auto* v = smt.find_or_construct<vector<InData> >("InDataVector")(smt.get_segment_manager());
            assert(v);
            return *v;
        }
    }
    
    
    int main(int argc, char* argv[]) {
        if(argc == 1){ //Parent process
            struct timeval tv;
            // there are making no sense 2 line in below, just examine
            gettimeofday(&tv, NULL);
            double time = ((double)tv.tv_usec/1000000);
            // Remove shared memory on construction and destruction
    
            // Create a new segment with given name and size
            struct shm_remove
            {
                shm_remove(){bip::shared_memory_object::remove("MySharedMemory");}
                ~shm_remove(){bip::shared_memory_object::remove("MySharedMemory");}
            }remover;
            Shared::segment smt(bip::create_only,"MySharedMemory", 65536); // 65536 for coliru
            auto& data = Shared::locate(smt);
            //Shared::alloc bip::alloc_inst (data);
            // Camera Capture 
            cv::Mat_<cv::Vec3b> mat;
            cv::VideoCapture vcap(0);
    
            InData id;
            // camera open check
            if (!vcap.isOpened())
                return -1;
    
            while (1) { // while keyboard key push
                vcap >> mat; // camera to mat
                int image_size = mat.total() * mat.elemSize();
                id.sizeImg = image_size;
                id.image.resize(image_size * sizeof(uchar));
                memcpy(&id.image[0], mat.data, image_size * sizeof(uchar));
                // get microsecond by double
                gettimeofday(&tv, NULL);
                double time = ((double)tv.tv_usec/1000000);
                id.x = time;
                data.push_back(id);
                if(cv::waitKey(30) >= 0) break; // keyboard pushed
            }
            //Launch child process
            std::string s(argv[0]); s += " child";
            if(0 != std::system(s.c_str()))
                return 1;
    
            // check child has destroyed the vector
            if(segment.find<vector<InData>>("InDataVector").first)
                return 1;
            }
        }else{
            // Open the managed segment
            managed_shared_memory segment(open_only, "MySharedMemory");
    
            // Find the vector 
            vector<InData> *myvector = segment.find<vector<InData>>("InDataVector").first;
            // Use vector in reverse order
    
            vector<InData>::iterator it;
    
            cv::Mat_<cv::Vec3b> im;
            for(it = myvector->begin(); it !=myvector->end(); ++it){
                im.resize(it->sizeImg);
                memcpy(im.data, &imref[0], it->sizeImg);
                cv::imshow("window1", im);
            }
    
            segment.destroy<vector<InData>>("InDataVector");
    
            return 0;
        }
    }
    
[/code]


CC BY-SA 3.0
2017-01-03T05:27:36.043
31583
2017-01-04T01:55:11.170
2017-05-23T12:38:56.467
-1
19922
question
c++ ubuntu opencv boost
boost.interprocessでの複雑な構造体ベクターと型変換についてコンパイルエラーがあります。


`id`は`Shared`名前空間の`InData`型である必要がありますが，グローバル名前空間の`InData`型になってしまっています．なので，

[code]

    InData id;
    
[/code]

を

[code]

    Shared::InData id;
    
[/code]

にするととりあえずこのコンパイルエラーは直ります．  
ただ，このままgccでコンパイルすると`error: could not convert ‘<brace-enclosed initializer
list>()’ from ‘<brace-enclosed initializer list>’ to
‘boost::interprocess::allocator<char,
boost::interprocess::segment_manager<char,
boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family>,
boost::interprocess::iset_index> >’`というエラーが出ます．  
これは`Shared::InData`構造体のコンストラクタが`alloc={}`となっているのが正しくないためです．なので，

[code]

    Shared::InData id(smt.get_segment_manager());
    
[/code]

とすると無事コンパイルできるはずです．

C++に慣れている人にプログラムの作成を依頼されることを強くお勧めします．


CC BY-SA 3.0
2017-01-03T11:06:44.547
31590
2017-01-03T11:06:44.547
4548
31583
answer