
On Sat, Oct 9, 2010 at 7:53 AM, OvermindDL1 <overminddl1@gmail.com> wrote:
On Sat, Oct 9, 2010 at 4:11 AM, alfC <alfredo.correa@gmail.com> wrote:
On Oct 9, 2:24 am, alfC <alfredo.cor...@gmail.com> wrote:
On Oct 8, 8:00 pm, OvermindDL1 <overmind...@gmail.com> wrote:
On Fri, Oct 8, 2010 at 6:57 PM, Joel de Guzman
<j...@boost-consulting.com> wrote:
On 10/9/2010 2:44 AM, alfC wrote:
On Oct 6, 5:33 pm, Joel de Guzman<j...@boost-consulting.com> wrote:
> On 10/7/2010 3:53 AM, alfC wrote:
>> Hi,
>> I am trying to convert a boost::array into a fusion::vector. >> reinterpreting the memory from boost::array. It works for tuples but >> not fusion::vector, why is that. Is there a way to make it work? ( I >> was hoping that the memory layout is the same to make conversion from >> one to the other very easy.)
> Don't do that. It will *never* be guaranteed to work even if it works > now. The memory layout of fusion::vector is an internal implementation > detail and can change anytime.
The question is: is it guaranteed for boost::tuples<double, double, ...>? (it seems so, just by the PODness of tuples of PODs in its stated design.) If so, then it is a *feature* of boost::tuple.
No it is not. 1) It is not documented 2) It is not a POD 3) Anything with a reinterpret_cast is not guaranteed to work (you can only rely on reinterpret_cast only when casting back from a lost type e.g. through type erasure).
Disregarding any of that is playing with fire.
The previous posts a few posts ago seems overly complicated, I would just do this (suitably wrapped into a function to handle it, maybe named copy):
// Proper includes here...
struct set1stTo2nd { template<typename T> void operator()(T& t) const { using namespace boost::fusion; deref(begin(t)) = deref(next(begin(t))); }};
typedef boost::array<int,3> arrType; typedef boost::fusion::vector<int,int,int> vecType; typedef boost::fusion::vector<arrType&,vecType&> zipSeqType;
arrType arr(1,1,1); vecType vec(5,5,5);
for_each(zipSeqType(arr,vec), set1stTo2nd()); assert(arr == make_vector(5,5,5));
FINALLY! I got it. I feel better now.
It turns out that the correct line of code is
for_each( boost::fusion::zip_view<zipSeqType>(zipSeqType(arr2,vec1)), set1stTo2nd() );
you wrote the correct typedef but then didn't apply the zip_view function.
(Although, related to the original question, I am still a bit worried about too much unnecessary copy which seems unavoidable since the memory layout of array<double, N> and fusion::vector<double*N> is different.)
below is the full program that *works*:
#include<boost/array.hpp> #include <boost/fusion/container.hpp> #include <boost/fusion/include/container.hpp> #include <boost/fusion/adapted/boost_array.hpp> #include <boost/fusion/include/boost_array.hpp> #include <boost/fusion/algorithm/iteration/for_each.hpp> #include <boost/fusion/include/for_each.hpp> #include <boost/fusion/algorithm/transformation/zip.hpp> #include <boost/fusion/include/zip.hpp> #include <boost/fusion/view/zip_view.hpp> #include <boost/fusion/include/zip_view.hpp>
#include<iostream> using std::clog; using std::endl;
using namespace boost::fusion; struct set1stTo2nd { template<typename T> void operator()(T t) const { deref(boost::fusion::begin(t)) = deref(boost::fusion::next(boost::fusion::begin(t))); } };
typedef boost::array<double,3> arrType; typedef boost::fusion::vector<double,double,double> vecType; typedef boost::fusion::vector<arrType&,vecType&> zipSeqType;
int main(){ boost::array<double, 3> arr1={{1.0, 2.1, 3.2}}; clog << "arr1: " << arr1[0] << ", " << arr1[1] << ", " << arr1[2] << endl;
boost::fusion::vector<double, double, double> vec1(arr1); clog << "vec1: " << at_c<0>(vec1) << ", "<< at_c<1>(vec1) << ", " << at_c<2>(vec1) << endl;
boost::array<double, 3> arr2; for_each( boost::fusion::zip_view<zipSeqType>(zipSeqType(arr2,vec1)), set1stTo2nd() ); clog << "arr2: " << at_c<0>(arr2) << ", "<< at_c<1>(arr2) << ", " << at_c<2>(arr2) << endl; return 0; }
prints: arr1: 1, 2.1, 3.2 vec1: 1, 2.1, 3.2 arr2: 1, 2.1, 3.2
Have a good weekend, Alfredo
Yeah, my mistake, busy at work and not paying attention, I meant to have the fusion::zip there. :)
another subtlety is that the correct signature is struct set1stTo2nd { template<typename T> void operator()(T t) const // not T& t) const ...
_______________________________________________ Boost-users mailing list Boost-users@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/boost-users
-- Sie haben diese Nachricht erhalten, da Sie der Google Groups-Gruppe Boost Users beigetreten sind. Wenn Sie Nachrichten in dieser Gruppe posten möchten, senden Sie eine E-Mail an boostusers@googlegroups.com. Wenn Sie aus dieser Gruppe austreten möchten, senden Sie eine E-Mail an boostusers+unsubscribe@googlegroups.com. Besuchen Sie die Gruppe unter http://groups.google.com/group/boostusers?hl=de, um weitere Optionen zu erhalten.