Namespaces
Variants

std:: to_address

From cppreference.net
Memory management library
( exposition only* )
Allocators
Uninitialized memory algorithms
Constrained uninitialized memory algorithms
Memory resources
Uninitialized storage (until C++20)
( until C++20* )
( until C++20* )
( until C++20* )

Garbage collector support (until C++23)
(C++11) (until C++23)
(C++11) (until C++23)
(C++11) (until C++23)
(C++11) (until C++23)
(C++11) (until C++23)
(C++11) (until C++23)
헤더 파일에 정의됨 <memory>
template < class Ptr >
constexpr auto to_address ( const Ptr & p ) noexcept ;
(1) (C++20부터)
template < class T >
constexpr T * to_address ( T * p ) noexcept ;
(2) (C++20부터)

p 가 나타내는 주소를 p 가 가리키는 객체에 대한 참조를 형성하지 않고 획득합니다.

1) Fancy pointer 오버로드: 표현식 std:: pointer_traits < Ptr > :: to_address ( p ) 가 유효한 경우, 해당 표현식의 결과를 반환합니다. 그렇지 않으면 std :: to_address ( p. operator - > ( ) ) 를 반환합니다.
2) Raw pointer 오버로드: 만약 T 가 함수 타입인 경우, 프로그램은 ill-formed입니다. 그렇지 않은 경우, p 를 수정 없이 반환합니다.

목차

매개변수

p - fancy 또는 raw 포인터

반환값

p 와 동일한 주소를 나타내는 원시 포인터.

가능한 구현

template<class T>
constexpr T* to_address(T* p) noexcept
{
    static_assert(!std::is_function_v<T>);
    return p;
}
template<class T>
constexpr auto to_address(const T& p) noexcept
{
    if constexpr (requires{ std::pointer_traits<T>::to_address(p); })
        return std::pointer_traits<T>::to_address(p);
    else
        return std::to_address(p.operator->());
}

참고 사항

std::to_address p 가 객체가 생성된 저장소를 참조하지 않는 경우에도 사용할 수 있으며, 이 경우 std:: addressof ( * p ) 는 매개변수에 바인딩할 유효한 객체가 없기 때문에 사용할 수 없습니다.

std::to_address 의 fancy pointer 오버로드는 std:: pointer_traits < Ptr > 특수화를 검사합니다. 해당 특수화의 인스턴스화 자체가 잘못된 경우 (일반적으로 element_type 을 정의할 수 없기 때문), 이는 immediate context 외부에서 hard error를 발생시키고 프로그램을 ill-formed 상태로 만듭니다.

std::to_address std::contiguous_iterator 를 만족하는 반복자에서도 추가적으로 사용될 수 있습니다.

기능 테스트 매크로 표준 기능
__cpp_lib_to_address 201711L (C++20) 포인터를 원시 포인터로 변환하는 유틸리티 ( std::to_address )

예제

#include <memory>
template<class A>
auto allocator_new(A& a)
{
    auto p = a.allocate(1);
    try
    {
        std::allocator_traits<A>::construct(a, std::to_address(p));
    }
    catch (...)
    {
        a.deallocate(p, 1);
        throw;
    }
    return p;
}
template<class A>
void allocator_delete(A& a, typename std::allocator_traits<A>::pointer p)
{
    std::allocator_traits<A>::destroy(a, std::to_address(p));
    a.deallocate(p, 1);
}
int main()
{
    std::allocator<int> a;
    auto p = allocator_new(a);
    allocator_delete(a, p);
}

참고 항목

포인터와 유사한 타입에 대한 정보를 제공함
(클래스 템플릿)
[static] (C++20) (optional)
팬시 포인터(fancy pointer)로부터 원시 포인터를 얻음 ( pointer_to 의 역함수)
( std::pointer_traits<Ptr> 의 public static 멤버 함수)