1. ホーム
  2. c

モジュラスを用いたC加算

2023-08-04 07:23:57

質問

私は、以下のような興味深いCのコードに出会いました。 A + B を表示する興味深いCコードに出会いましたが、理解するのに苦労しています。

入力フォーマットです。

A B

ここで A , B の間の整数です。 010 をスペース1つで区切ってください。

コード

main( n )
{
    gets( &n );
    printf("%d", n % 85 - 43);
}

これは短いコーディングを意図したもので、警告は気にしないでください。

ここまでで理解できたこと

gets( &n ) の下位3バイトにA, space, BのASCII値を格納します。 n . 例えば A = 3B = 8n = 0x00382033 . 与えられた条件によって n がオーバーフローするのを防ぎます。しかし、私はどのように n % 85 - 43A + B .

どうやってこの数字を出すんだ?

どのように解決するのですか?

リトルエンディアンの int で (そして ASCII テキスト、8 ビットバイト、その他コードが必要とするすべての前提を仮定して)、コード内の技術的に間違っているモダン C のものをすべて無視して、あなたの "What I understand so far" は正しいのです。

gets(&n) の最初の 3 バイトに A、スペース、および B の ASCII 値を格納します。 n . また、4バイト目にはヌルターミネーターが格納されます。これらの ASCII 値をこれらのバイトに格納すると n のこれらのバイトに格納すると n が値をとる B*256*256 + space*256 + A である。 B , space そして A は対応するASCII値を表します。

256 mod 85は1なので、モジュラー算術の特性により。

(B*256*256 + space*256 + A) % 85 = (B + space + A) % 85

ちなみに、4バイトのビッグエンディアンのint型では、次のようになります。

(A*256*256*256 + space*256*256 + B*256) % 85 = (B + space + A) % 85

というわけで、4バイトのintであればエンディアンは関係ありません。(例えば8バイトのintだと n その gets が設定されなかった)

スペースはASCII32で、数字文字のASCII値は48+数字の値です。定義する ab を入力された数字の数値(数字文字のASCII値ではなく)とすると、次のようになります。

(B + space + A) % 85 = (b + 48 + 32 + a + 48) % 85
                     = (a + b + 128) % 85
                     = (a + b + 43) % 85

(B + space + A) % 85 - 43 = (a + b + 43) % 85 - 43
                          = (a + b) % 85
                          = a + b

ここで、最後の2つの等価性は、以下の事実に依存しています。 ab は0から9の値をとります。