以下のコードがあるとします。
class A {
uint32_t X;
uint32_t Y;
};
int main ()
{
A a;
uint64_t num = (uint64_t)a;
}
コンパイラは、「A から uint64_t に変換できません。ユーザー定義の変換演算子が定義されていません」というエラーを返します。
エラーは予期されたものですか? はいの場合、その理由は?
以下のコードがあるとします。
class A {
uint32_t X;
uint32_t Y;
};
int main ()
{
A a;
uint64_t num = (uint64_t)a;
}
コンパイラは、「A から uint64_t に変換できません。ユーザー定義の変換演算子が定義されていません」というエラーを返します。
エラーは予期されたものですか? はいの場合、その理由は?
1 つの値の 32 ビットを 64 ビット値の上位 32 ビットに明示的にコピーし、他の 32 ビットを 64 ビット値の下位 32 ビットに明示的にコピーする必要があります。
他のすべてのメソッドは、技術的に未定義の動作です (ただし、実装の詳細が十分にわかっている場合は機能します)。
class A
{
uint32_t X;
uint32_t Y;
uint64_t to64()
{
// convert X and Y to unsigned 64-bit ints
uint64_t x64 = X;
uint64_t y64 = Y;
// left-shift the 64-bit X 32 bits
x64 <<= 32;
// return the sum
return( x64 + y64 );
}
};
はるかに少ないコードで実行できますが、これは実行する必要があることを段階的に示しています。
表現の「エンディアン」を指定していません。x上位の単語と下位の単語になりたい場合yは、キャスト演算子をクラスに追加できます。
explicit operator uint64_t () const noexcept
{
return ((static_cast<uint64_t>(X) << 32) | Y);
}
'(uint64_t) obj'または (理想的には)この'static_cast<uint64_t>(obj)'メソッドを呼び出します。explicit暗黙的に呼び出されるのを防ぎます - これはおそらく私が一日中言った中で最もばかげたことです - しかし、それは驚きを防ぎます。<cstdint>と を使用した場合の追加ポイントstd::uint64_t。