convert data type help

R

Rex_chaos

Hi all,
I have a question about datatype converting. Consider the following
types
std::complex<double>
and
struct MyComplex
{
double re, im;
}

I have a larger array of std::complex being converted to that of
MyComplex

I have tried std::transform plus a self-defined converting function.
It works but the efficiency is very low.

I also tried the following method.

std::complex<double> *a;
MyComplex *b;

//initialize a, b
b = reinterpret_cast<MyComplex*>(a);

Yes. Now it's so fast!!! However, I found that the address of a and b
are the same after casting. That is, one of the allocated memory will
be lost!!! That's too bad. Please help!
 
A

Attila Feher

Rex_chaos said:
Hi all,
I have a question about datatype converting. Consider the following
types
std::complex<double>
and
struct MyComplex
{
double re, im;
}

I have a larger array of std::complex being converted to that of
MyComplex

I have tried std::transform plus a self-defined converting function.
It works but the efficiency is very low.

I also tried the following method.

std::complex<double> *a;
MyComplex *b;

//initialize a, b
b = reinterpret_cast<MyComplex*>(a);

Yes. Now it's so fast!!! However, I found that the address of a and b
are the same after casting. That is, one of the allocated memory will
be lost!!! That's too bad. Please help!

I would rather get rid off MyComplex by defining it (using typedef) to be
std::complex<double>.

The hack you do with reinterpret cast is at best non-portable, but I would
say it is so non-portable, that applying a compiler/standard library patch
might kill it.

In this case transform is The Right Thing to do. Try to profile the
transformation (in a simple test program) to see what is slow. If the
transform algorithm is slow, you might overcome that with a hand-made loop.
If the actual copying of the elements is slow (or memory allocation for the
new element) that is unfortunately the trade-off you have to pay for using
two types.
 
T

tom_usenet

It is both portable and likely to become standard. See e.g.
http://std.dkuug.dk/jtc1/sc22/wg21/docs/papers/2002/n1356.html

Actually, scrub that, the reinterpret cast is strictly speaking only
portable if the cast is to an array of double or the C99 type
_Complex, although I doubt there is a platform on which it would fail
to "do the right thing".

However, if sizeof(MyComplex) == sizeof(double) * 2, then it will
work, but it isn't yet standard.

Tom
 
T

tom_usenet

Hi all,
I have a question about datatype converting. Consider the following
types
std::complex<double>
and
struct MyComplex
{
double re, im;
}

I have a larger array of std::complex being converted to that of
MyComplex

I have tried std::transform plus a self-defined converting function.

You should use a converting functor. e.g.

struct ComplexConverter
{
MyComplex operator()(std::complex<double> const& c) const
{
MyComplex mc = {c.real(), c.imag()};
return mc;
}
};
It works but the efficiency is very low.

With the above change, efficiency should be much much higher (when
compiled with maximum optimization), since the conversion calls will
be inlined, whereas the calls through a function pointer probably were
not.
I also tried the following method.

std::complex<double> *a;
MyComplex *b;

//initialize a, b
b = reinterpret_cast<MyComplex*>(a);

Yes. Now it's so fast!!! However, I found that the address of a and b
are the same after casting. That is, one of the allocated memory will
be lost!!!

Well, just take a copy of it! e.g.

MyComplex* sufficientSpace = ...;
std::copy(b, b + numElements, sufficientSpace);
That's too bad. Please help!

std::complex<double> isn't a POD type, so the cast isn't guaranteed to
work. However, as long as sizeof(std::complex<double>) ==
sizeof(MyComplex) == sizeof(double) * 2, it *should* work. Look out
for the C99 _Complex type, which might help you out.

Tom
 
A

Attila Feher

tom_usenet said:
Actually, scrub that, the reinterpret cast is strictly speaking only
portable if the cast is to an array of double or the C99 type
_Complex, although I doubt there is a platform on which it would fail
to "do the right thing".

However, if sizeof(MyComplex) == sizeof(double) * 2, then it will
work, but it isn't yet standard.

Ahem. *If* the order of the real/imaginary members is the same!
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,766
Messages
2,569,569
Members
45,042
Latest member
icassiem

Latest Threads

Top