1. 程式人生 > 其它 >取模運算性質

取模運算性質

前言

取模運算(C++中用符號%表示)是求兩個數相除的餘數。其概念與取餘操作類似,又不完全相同。

一.運算定義

假設有整數a,b,在C++中,對於a%b:

1.取a,b絕對值進行運算取餘。

2.運算結果符號與a相同。

二.基本性質

作為一種運算,與加減乘除類似,也有交換律,結合律,分配律。

1.交換律

\[(a+b)\%p=(b+a)\%p \] \[(a\times b)\%p=(b\times a)\%p \]

2.結合律

\[((a+b)\; \%p +c)\%p = ((a+(b+c)\; \%p))\;\%p \] \[((a\times b)\; \%p \times c)\%p = ((a\times (b\times c)\; \%p))\;\%p \]

3.分配率

比較坑的就是當\(\%p\)移入到括號以內後,外部的\(\%p\)仍然需要保留。

\[(a+b)\%p=(a\%p+b\%p) \;\% p \] \[(a-b)\%p=(a\%p-b\%p) \% p \] \[(a\times b)\%p=(a\%p\times b\%p) \% p \] \[a^b\;\%p=((a\;\%p)^{b\;\%p}) \% p \]

三.應用

求解\(a\times b\; mod\;p\)

快速冪的程式碼如下

    int a, b, p;
    cin >> a >> b >> p;
    int res = 1 % p;
    while (b) {
        if (b & 1) res = (long long)res * a % p;
        a = (long long)a * a % p;
        b >>= 1;
    }
    cout << res << endl;

我們由快速冪的計算原理,可知\(a\times b\)可拆成\(a\times{c_{k-1}2^{k-1}}+ a\times{c_{k-2}2^{k-2}}+...+ a\times{c_02^0}\)的迭代形式來計算。

根據以上的加法分配率,\(a\times b\; \%p\),則可以改寫成\((a\times{c_{k-1}2^{k-1}}\; \%p+ a\times{c_{k-2}2^{k-2}}\; \%p+...+ a\times{c_02^0}\; \%p)\;\%p\),因此在快速冪的程式碼中可以用a = (long long)a * a % p;res = (long long)res * a % p;

進行表示。

四. 後記

因為在做題時因為概念理解不透徹,備受折磨,因此進行整理。