Use list initialization to construct B
. The elements are then guaranteed to be evaluated from left to right.
C(std::unique_ptr<A> a) : B{a->x, std::move(a)} {}
// ^ ^ - braces
From ยง8.5.4/4 [dcl.init.list]
Within the initializer-list of a braced-init-list, the initializer-clauses, including any that result from pack expansions (14.5.3), are evaluated in the order in which they appear. That is, every value computation and side effect associated with a given initializer-clause is sequenced before every value computation and side effect associated with any initializer-clause that follows it in the comma-separated list of the initializer-list.