Re: [eigen] Map's and not Maps |
[ Thread Index |
Date Index
| More lists.tuxfamily.org/eigen Archives
]
- To: eigen@xxxxxxxxxxxxxxxxxxx
- Subject: Re: [eigen] Map's and not Maps
- From: "Benoit Jacob" <jacob.benoit.1@xxxxxxxxx>
- Date: Mon, 8 Dec 2008 20:40:32 +0100
- Dkim-signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=gamma; h=domainkey-signature:received:received:message-id:date:from:to :subject:in-reply-to:mime-version:content-type :content-transfer-encoding:content-disposition:references; bh=NegfqyQI1oZMZC3KVim1RzkFIXHbE/xaVGTt9d1K/tQ=; b=EKhMLccZKQiT5ESGYPxcZujKFXopuZG4TbYZY0dyAFiq3di8jp/GH5GbvxQBtYxcuy J2UNJv70q23OY/2ipio95IosX3XrgjRc9hPim+5AwkeBaJT1auI+dqDFoJfMoKtfPAdo +Qvvm3bttYUZnP3hABNWrTCz4DNyKbdQOs/6Q=
- Domainkey-signature: a=rsa-sha1; c=nofws; d=gmail.com; s=gamma; h=message-id:date:from:to:subject:in-reply-to:mime-version :content-type:content-transfer-encoding:content-disposition :references; b=HRy+GCODDFEmBzocb1EIQO+MjlXo1RSQtZikexGjsbLVG/IPfIrYtZuYPQj/uTFH3u cAP/YWunuqP2ussGjl1a5JNRxtpcFgo3vsF2fe1AM26CboBc8P2BQglyaiawQmNxFJaP DL90vomFp3nJwKX/glzDjUwRqzq/khz+KL3c8=
But just FYI, while we're at it, there are a few ways in which already
today you can use Eigen to vectorize operations on Vector3f's.
For example suppose you have a dynamic array of n Vector3f's. You
could replace it with a single matrix of type
Matrix<float, 3, Eigen::Dynamic> matrix(3, n);
i.e. the i-th column is the i-th vector from your array.
Then, for many operations, Eigen is able to treat the whole matrix as
a single vector of length 3*n. This allows Eigen to perform some very
efficient vectorization. Inside Eigen, we call that
LinearVectorization.
For example, if you add two such matrices, Eigen vectorizes that very
well as a single addition of vectors of length 3*n, for any n (if it's
not a multiple of 4 Eigen will finish the last few coefficients
without vectorization).
Cheers,
Benoit
2008/12/8 Keir Mierle <mierle@xxxxxxxxx>:
>
>
> On Mon, Dec 8, 2008 at 4:07 AM, Benoit Jacob <jacob.benoit.1@xxxxxxxxx>
> wrote:
>>
>> I think that Benjamin was only asking for it to be possible at all,
>> letting alone vectorization... hence your example,
>>
>> > template<Derived>
>> > float SomeCoolFunction(MatrixBase<Derived>& v, void* somedata)
>> > {
>> > EIGEN_STATIC_ASSERT_VECTOR_SPECIFIC_SIZE(Derived,3);
>> > // ...
>> > }
>>
>> is, as far as I understand, exactly what he is asking for.
>>
>> Benjamin: Yes you can make a SomeCoolFunction that takes seamlessly
>> either a Vector3f or a Map<Vector3f>, that is done as above, actually
>> this construction occurs all over the place in Eigen.
>>
>> Anyway there is no vectorization possible for Vector3f at all because
>> 3*sizeof(float) == 12 <sizeof_a_packet == 16.
>
> Since 2 and 3 are quite common operations it might be worth investigating if
> it's faster to do vectorized 4-ops where the last elements are ignored.
>
> For example, for element wise multiply, pack the three elements into the
> 4-wide register, put a zero in the last register, then ignore the result in
> last element.
>
> It's probably necessary to benchmark if such a hack is worthwhile.
>
> Cheers,
> Keir
>
>
>>
>>
>> Cheers,
>> Benoit
>>
>> 2008/12/8 Gael Guennebaud <gael.guennebaud@xxxxxxxxx>:
>> >
>> > Hi,
>> >
>> > you guessed right, the major issue avoiding such a construction is owing
>> > to
>> > the alignment of the data. Indeed, the vectorization of some fixed size
>> > vector/matrix types assume that the data are correctly aligned. So, in a
>> > general, you cannot avoid to generate 2 versions of SomeCoolFunction,
>> > one
>> > with the vectorization and one without (see below).
>> >
>> > In the very specific cases where the vectorization is disabled and/or
>> > you
>> > know the vector type won't be vectorized by Eigen or you know the data
>> > are
>> > aligned, then you can still simply cast your pointer:
>> >
>> > float result = SomeCoolFunction(*reinterpret_cast<Vector3f*>(inputdata),
>> > bla);
>> >
>> > For instance, for Vector3f this is always ok because this type cannot be
>> > vectorized. (if we forget the use of reinterpret_cast which is not super
>> > clean)
>> >
>> >
>> > A much more general solution is to template SomeCoolFunction and use
>> > static
>> > assertions to check the input types, eg:
>> >
>> > template<Derived>
>> > float SomeCoolFunction(MatrixBase<Derived>& v, void* somedata)
>> > {
>> > EIGEN_STATIC_ASSERT_VECTOR_SPECIFIC_SIZE(Derived,3);
>> > // ...
>> > }
>> >
>> > The advantage of this approach is that you can take as input any vector
>> > expression like a sub vector of a matrix:
>> >
>> > SomeCoolFunction(mat33.col(1), bla);
>> >
>> > A drawback might be that the same code could be generated multiple time
>> > (though the compiler/linker are supposed to be able to factorize such
>> > redundancies automatically, but I don't really trust them for that).
>> >
>> > I agree that this solution is not optimal from a user perspective, but
>> > currently I cannot see any better solution to that issue.
>> >
>> > Cheers,
>> > Gael.
>> >
>> >
>> > On Mon, Dec 8, 2008 at 12:06 PM, Benjamin Schindler
>> > <bschindler@xxxxxxxxxxxxxxx> wrote:
>> >>
>> >> Hi
>> >>
>> >> There is currently one thing which I really don't like atm in eigen.
>> >> For
>> >> ease, I use a lot of direct vector's. But all the data I get from
>> >> outside is
>> >> in the form of pointers, so I have to use maps. One thing I would
>> >> really
>> >> love to have is a way to be able to do the following:
>> >>
>> >> float SomeCoolFunction(Vector3f& v, void* somedata);
>> >> ...
>> >> Map<Vector3f> input(inputdata);
>> >> float result = SomeCoolFunction(input, bla);
>> >>
>> >> This is currently not possibel and I'm not sure what exactly is needed
>> >> to
>> >> support this kind of stuff and in which way this would impact
>> >> performance
>> >> (One can't assume alignment for example etc). But from a design
>> >> perspective,
>> >> this would be just amazing :)
>> >>
>> >> Any comments?
>> >> Benjamin
>> >>
>> >> ---
>> >>
>> >
>> >
>>
>> ---
>>
>
>
---