たとえば、私が持っている場合、
int a = 42;
unsigned b = 10;
int c = a + b;
このステートメントでは、最初にに変換されますint c = a + b;
か、それとも?に変換されますか?両方とも同じ変換ランクを持っているので、どちらが変換されるかをどのようにして知ることができますか?標準ルールはありますか?a
unsigned int
b
signed int
unsigned int
signed
簡単な回答: C99 6.3.1.8-p1 に従って、a
s の値は、C99 6.3.1.3-p2 に従って、UINT_MAX+1 が で許可されている範囲に収まるまで追加され、unsigned int に変換されunsigned int
ます。すでにその範囲内にあるため、追加は実行されません。C99 6.3.1.3-p3 までに、int c
(p1) と (p2) が適用されない場合、割り当てられた結果は実装定義になります。ただし、この場合、6.3.1.3-p1 の「値」節に注意してください。この場合の値 (52) はで表すことができるint
ので、変更せずに定義します。
C99 6.3.1.3 符号付きおよび符号なし整数
整数型の値が _Bool 以外の別の整数型に変換される場合、その値が新しい型で表現できる場合、その値は変更されません。
それ以外の場合、新しい型が符号なしの場合、値が新しい型の範囲内になるまで、新しい型で表現できる最大値よりも 1 つ多い値を繰り返し加算または減算することによって、値が変換されます60)。
それ以外の場合、新しい型は署名され、値を表現できません。結果が実装定義であるか、実装定義のシグナルが発生します。
C99 6.3.1.8 通常の算術変換
算術型のオペランドを期待する多くの演算子は、同様の方法で変換を行い、結果の型を生成します。目的は、オペランドと結果の共通の実数型を決定することです。指定されたオペランドについて、各オペランドは型 domain を変更せずに、対応する実数型が共通実数型である型に変換されます。特に明記しない限り、共通実数型は、結果の対応する実数型でもあります。その型ドメインは、オペランドが同じ場合はオペランドの型ドメインであり、そうでない場合は複素数です。このパターンは、通常の算術変換と呼ばれます。
まず、いずれかのオペランドの対応する実数型が long double の場合、もう一方のオペランドは、型 domain を変更せずに、対応する実数型が long double である型に変換されます。
それ以外の場合、いずれかのオペランドの対応する実数型が double の場合、もう一方のオペランドは、型 domain を変更せずに、対応する実数型が double である型に変換されます。
それ以外の場合、いずれかのオペランドの対応する実数型が float の場合、もう一方のオペランドは、型ドメインを変更せずに、対応する実数型が float である型に変換されます.62)
それ以外の場合、両方のオペランドで整数昇格が実行されます。次に、プロモートされたオペランドに次の規則が適用されます。
両方のオペランドが同じ型の場合、それ以上の変換は必要ありません。
それ以外の場合、両方のオペランドが符号付き整数型であるか、または両方が符号なし整数型である場合、整数変換ランクが小さい型のオペランドは、ランクが大きいオペランドの型に変換されます。
それ以外の場合、符号なし整数型のオペランドのランクが他のオペランドの型のランク以上である場合、符号付き整数型のオペランドは符号なし整数型のオペランドの型に変換されます。
それ以外の場合、符号付き整数型のオペランドの型が符号なし整数型のオペランドの型のすべての値を表すことができる場合、符号なし整数型のオペランドは符号付き整数型のオペランドの型に変換されます。
それ以外の場合、両方のオペランドは、符号付き整数型のオペランドの型に対応する符号なし整数型に変換されます。