ホームページ > バックエンド開発 > C++ > C では `i = i` は常に未定義の動作ですか?

C では `i = i` は常に未定義の動作ですか?

Patricia Arquette
リリース: 2024-12-07 03:00:11
オリジナル
874 人が閲覧しました

Is `i  =   i` Always Undefined Behavior in C  ?

未定義の動作とシーケンス ポイントの再検討

組み込み型の未定義の動作

前回の記事「未定義の動作とシーケンス ポイント」では、に関連する潜在的な未定義の動作について説明しました。式:

i += ++i;
ログイン後にコピー

i が組み込み型の場合、オブジェクト i は連続するシーケンス ポイント間で 2 回変更されるため、この式は未定義の動作を呼び出します。

ユーザー定義型の未定義の動作

ただし、i がユーザー定義型 (定義された Index クラスなど) の場合以下:

class Index
{
    int state;

    public:
        Index(int s) : state(s) {}
        Index& operator++()
        {
            state++;
            return *this;
        }
        Index& operator+=(const Index & index)
        {
            state+= index.state;
            return *this;
        }
        operator int()
        {
            return state;
        }
        Index & add(const Index & index)
        {
            state += index.state;
            return *this;
        }
        Index & inc()
        {
            state++;
            return *this;
        }
};
ログイン後にコピー

式 i = i はまだ未定義の動作を呼び出しますか?

オーバーロードされた演算子の適切に定義された動作

驚くべきことに、いいえです。ユーザー定義型 i の式 i = i は、オーバーロードされた演算子が C の関数とみなされるため、未定義の動作を引き起こしません。 C ISO 標準のセクション 1.9.17 によると:

関数を呼び出すとき (関数がインラインであるかどうかに関係なく)、すべての関数引数の評価後にシーケンス ポイントがあります...

したがって、演算子および演算子 = 関数の呼び出しにはシーケンス ポイントが導入され、未定義の動作が防止されます。

a[ i] = の未定義の動作i

式 a[ i] = i は、 a がオーバーロードされた添字演算子を持つユーザー定義型である場合にも、 i 式の評価後にシーケンス ポイントを持つ関数呼び出しとみなされるため、適切に定義されています。 .

i の明確に定義された動作

C 03 では、式 i は事実上同等であるため、明確に定義されています。 to:

((i.operator++()).operator++()).operator++();
ログイン後にコピー

各関数呼び出しでシーケンス ポイントが導入され、式が明確に定義されます。

以上がC では `i = i` は常に未定義の動作ですか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

ソース:php.cn
このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。
著者別の最新記事
人気のチュートリアル
詳細>
最新のダウンロード
詳細>
ウェブエフェクト
公式サイト
サイト素材
フロントエンドテンプレート