< cpp‎ | types
Utilities library
General utilities
Relational operators (deprecated in C++20)
Integer comparison functions
Swap and type operations
Common vocabulary types

Elementary string conversions
Type support
Basic types
Fundamental types
Fixed width integer types (C++11)
Numeric limits
C numeric limits interface
Runtime type information
Type traits
Type categories
Type properties
(C++11)(until C++20)
(C++11)(deprecated in C++20)
Type trait constants
Constant evaluation context
Supported operations
Relationships and property queries
Type modifications
Type transformations
(C++11)(until C++20)(C++17)
Defined in header <cstddef>
#define offsetof(type, member) /*implementation-defined*/

The macro offsetof expands to an integral constant expression of type std::size_t, the value of which is the offset, in bytes, from the beginning of an object of specified type to its specified subobject, including padding if any.

Given an object o of type type and static storage duration, o.member shall be an lvalue constant expression that refers to a subobject of o. Otherwise, the behavior is undefined. Particularly, if member is a static data member, a bit-field, or a member function, the behavior is undefined.

If type is not a PODType (until C++11)standard layout type (since C++11), the behavior is undefined (until C++17)use of the offsetof macro is conditionally-supported (since C++17).

The expression offsetof(type, member) is never type-dependent and it is value-dependent if and only if type is dependent.


[edit] Exceptions

offsetof throws no exceptions.

The expression noexcept(offsetof(type, member)) always evaluates to true.

(since C++11)

[edit] Notes

The offset of the first member of a standard-layout type is always zero (empty-base optimization is mandatory).

(since C++11)

offsetof cannot be implemented in standard C++ and requires compiler support: GCC, LLVM.

member is not restricted to a direct member. It can denote a subobject of a given member, such as an element of an array member. This is specified by C DR 496.

It is specified in C23 that defining a new type in offsetof is undefined behavior, and such usage is only partially supported by some implementations in C++ modes: offsetof(struct Foo { int a; }, a) is supported by ICC and some old versions of GCC, while offsetof(struct Foo { int a, b; }, a) is rejected by all known implementations because of the comma in the definition of Foo.

[edit] Example

#include <iostream>
#include <cstddef>
struct S {
    char   m0;
    double m1;
    short  m2;
    char   m3;
//  private: int z; // warning: 'S' is a non-standard-layout type
int main()
        << "offset of char   m0 = " << offsetof(S, m0) << '\n'
        << "offset of double m1 = " << offsetof(S, m1) << '\n'
        << "offset of short  m2 = " << offsetof(S, m2) << '\n'
        << "offset of char   m3 = " << offsetof(S, m3) << '\n';

Possible output:

offset of char   m0 = 0
offset of double m1 = 8
offset of short  m2 = 16
offset of char   m3 = 18

[edit] Defect reports

The following behavior-changing defect reports were applied retroactively to previously published C++ standards.

DR Applied to Behavior as published Correct behavior
CWG 273 C++98 offsetof may not work if unary operator& is overloaded required to work correctly even if operator& is overloaded

[edit] See also

unsigned integer type returned by the sizeof operator
(typedef) [edit]
checks if a type is a standard-layout type
(class template) [edit]
C documentation for offsetof