Вопрос

Есть ли способ обеспечить выравнивание контейнеров STL с конкретным байтом, используя атрибут((выровнен)) Возможно? Целевые компиляторы не являются Microsoft Visual C ++.

Какие библиотеки, если таковые имеются, предоставляют специализированные шаблоны алгоритмов STL, которые имеют специфическую явную векторизацию, например. Мои компиляторы, представляющие интерес, - G ++, Intel и IBM XL.

Это было полезно?

Решение

С помощью контейнеров STL вы можете предоставить свой собственный распределитель с помощью дополнительного параметра шаблона. Я бы не рекомендовал писать целый распределитель с нуля, но вы могли бы написать тот, который просто обертка вокруг new а также delete но гарантирует, что возвращенная память соответствует вашим требованиям выравнивания. (Например, если вам нужно n байты с 16-байтовым выравниванием, вы используете new выделить n + 15 байты и верните указатель на первый 16-байтовый выравниваемый адрес в этом блоке.)

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

Другие советы

Вам нужен индивидуальный распределитель. Вы можете построить один на std::allocator довольно легко:

template <typename T, size_t TALIGN=16, size_t TBLOCK=8>
class aligned_allocator : public std::allocator<T>
{
public:
     aligned_allocator() {}
     aligned_allocator& operator=(const aligned_allocator &rhs){
         std::allocator<T>::operator=(rhs);
         return *this;
     }

     pointer allocate(size_type n, const void *hint){
         pointer p = NULL;
         size_t count = sizeof(T) * n;
         size_t count_left = count % TBLOCK;
         if( count_left != 0 )
         {
             count += TBLOCK - count_left;
         }
         if ( !hint )
         {
             p = reinterpret_cast<pointer>(aligned_malloc(count,TALIGN));
         }else{
             p = reinterpret_cast<pointer>(aligned_realloc((void*)hint,count,TALIGN));
         }
         return p;
     }

     void deallocate(pointer p, size_type n){
         aligned_free(p);
     }

     void construct(pointer p, const T &val){
         new(p) T(val);
     }

     void destroy(pointer p){
         p->~T();
     }
};

Единственное, чего здесь не хватает, это aligned_malloc, aligned_realloc а также aligned_free. Анкет Вам либо нужно реализовать их самостоятельно (не должно быть так сложно), либо найти версии тех, кто в Интернете (я видел хотя бы один в Огр двигатель).

У вас уже есть хорошие ответы, но, похоже, стоит добавить, что C ++ 0x включает в себя std::align(), что должно облегчить реализацию подобных вещей.

Вам нужен пользовательский распределитель, который возвращает выровненное хранилище. Это должно решить вашу проблему.

Вместо того, чтобы писать свой собственный распределитель, как предложено раньше, вы можете использовать boost::alignment::aligned_allocator.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top