Пространства имён
Варианты
Действия

std::align

Материал из cppreference.com
< cpp‎ | memory
 
 
Библиотека утилит
Языковая поддержка
Поддержка типов (базовые типы, RTTI)
Макросы тестирования функциональности библиотеки (C++20)    
Управление динамической памятью
Программные утилиты
Поддержка сопрограмм (C++20)
Вариативные функции
Трёхстороннее сравнение (C++20)
(C++20)
(C++20)(C++20)(C++20)(C++20)(C++20)(C++20)
Общие утилиты
Дата и время
Функциональные объекты
Библиотека форматирования (C++20)
(C++11)
Операторы отношения (устарело в C++20)
Целочисленные функции сравнения
(C++20)(C++20)(C++20)    
(C++20)
Операции обмена и типа
(C++14)
(C++11)
(C++11)
(C++11)
(C++17)
Общие лексические типы
(C++11)
(C++17)
(C++17)
(C++17)
(C++11)
(C++17)
(C++23)
Элементарные преобразования строк
(C++17)
(C++17)
 
Динамическое управление памятью
no section name
Ограниченные алгоритмы неинициализированной памяти
no section name
Поддержка сбора мусора
(C++11)(до C++23)
(C++11)(до C++23)
(C++11)(до C++23)
(C++11)(до C++23)
(C++11)(до C++23)
(C++11)(до C++23)



no section name
 
Определено в заголовочном файле <memory>
void* align( std::size_t alignment,

             std::size_t size,
             void*& ptr,

             std::size_t& space );
(начиная с C++11)

Учитывая указатель ptr на буфер размером space, возвращает указатель, выровненный по указанному alignment для числа байтов size, и уменьшает аргумент space по количеству байтов, используемых для выравнивания. Возвращается первый выровненный адрес.

Функция изменяет указатель только в том случае, если можно было бы поместить в буфер требуемое количество байтов, выровненных по заданному выравниванию. Если буфер слишком мал, функция ничего не делает и возвращает nullptr.

Поведение не определено, если alignment не является степенью двойки.

Содержание

[править] Параметры

alignment желаемое выравнивание
size размер хранилища для выравнивания
ptr указатель на непрерывное хранилище (буфер) размером не менее space байт
space размер буфера для операции

[править] Возвращаемое значение

Скорректированное значение ptr или значение нулевого указателя, если предоставленное пространство слишком мало.

[править] Пример

Демонстрирует использование std::align для размещения в памяти объектов разных типов.

#include <iostream>
#include <memory>
 
template<std::size_t N>
struct MyAllocator
{
    char data[N];
    void* p;
    std::size_t sz;
    MyAllocator() : p(data), sz(N) {}
    template<typename T>
    T* aligned_alloc(std::size_t a = alignof(T))
    {
        if (std::align(a, sizeof(T), p, sz))
        {
            T* result = reinterpret_cast<T*>(p);
            p = (char*)p + sizeof(T);
            sz -= sizeof(T);
            return result;
        }
        return nullptr;
    }
};
 
int main()
{
    MyAllocator<64> a;
    std::cout << "распределяет a.data в " << (void*)a.data
              << " (" << sizeof a.data << " байт)\n";
 
    // распределяет char
    if (char* p = a.aligned_alloc<char>())
    {
        *p = 'a';
        std::cout << "распределяет char в " << (void*)p << '\n';
    }
 
    // распределяет int
    if (int* p = a.aligned_alloc<int>())
    {
        *p = 1;
        std::cout << "распределяет int в " << (void*)p << '\n';
    }
 
    // распределяет int, выровненный по 32-байтовой границе
    if (int* p = a.aligned_alloc<int>(32))
    {
        *p = 2;
        std::cout << "распределяет int в " << (void*)p << " (выравнивание по 32 байтам)\n";
    }
}

Возможный вывод:

распределяет a.data в 0x7ffd0b331f80 (64 байт)
распределяет char в 0x7ffd0b331f80
распределяет int в 0x7ffd0b331f84
распределяет int в 0x7ffd0b331fa0 (выравнивание по 32 байтам)

[править] Отчёты о дефектах

Следующие изменения поведения были применены с обратной силой к ранее опубликованным стандартам C++:

Номер Применён Поведение в стандарте Корректное поведение
LWG 2377 C++11 alignment должен быть основным или поддерживаемым
расширенным значением выравнивания
должен быть только степенью двойки

[править] Смотрите также

оператор alignof(C++11) запрашивает требования к выравниванию типа[править]
спецификатор alignas(C++11) указывает, что хранилище для переменной должно быть выровнено на определённую величину[править]
(C++11)(устарело в C++23)
определяет тип, подходящий для использования в качестве неинициализированного хранилища для типов заданного размера
(шаблон класса) [править]
сообщает компилятору, что указатель выровнен
(шаблон функции) [править]