深度學習演算法很大程度上基於矩陣運算。例如神經網路中的全連線,本質上是乙個矩陣乘法;而卷積運算也通常是用矩陣乘法來完成的。有一些科研工作者為了讓神經網路的計算更快捷,提出了二值化網路的方法,就是將網路權重壓縮成只用兩種值表示的形式,這樣就可以用一些 trick 加速計算了。例如兩個二進位制向量點乘,可以用計算機中的與運算代替,然後統計結果中 1 的個數即可。
然而有時候為了降低壓縮帶來的誤差,只允許其中乙個矩陣被壓縮成二進位制。這樣的情況下矩陣乘法運算還能否做進一步優化呢?給定兩個整數矩陣a, b,計算矩陣乘法 c = a x b。為了減少輸出,你只需要計算 c 中所有元素的的異或和即可。
第一行有三個整數 n, p, m, 表示矩陣 a, b 的大小分別是 n x p, p x m 。接下來 n 行是矩陣 a 的值,每一行有 p 個數字。第 i+1 行第 j 列的數字為 ai,j, ai,j 用大寫的16進製表示(即只包含 0~9, a~f),每個數字後面都有乙個空格。
接下來 m 行是矩陣 b 的值,每一行是乙個長為 p 的 01字串。第 i + n + 1 行第 j 個字元表示 bj,i 的值。
乙個整數,矩陣 c 中所有元素的異或和。示例1複製
4 2 3複製3 48 a
f 56 7
0111
10
2
矩陣 c 的值為:4 7 3
10 18 8
5 20 15
7 13 6
2 ≤ n, m ≤ 4096, 1 ≤ p ≤ 64, 0 ≤ ai,j< 65536.思路:
![](https://pic.w3help.cc/894/eda3deb5bed488848422c0e0857fa.jpeg)
p最多64,那麼可將矩陣a的每一行縱向切割,最多切割8塊,矩陣b的每一列,橫向切割,最多切割8塊,矩陣b是01串,那麼每一列的每一塊的值就有256種,可將矩陣a與矩陣b分塊後這256種情況相乘的結果先預處理求出來,再進行求最後答案。大概就是通過減小p值(矩陣分塊)來降低複雜度的吧~
**如下:
#include#include#include#include#include#include#include#include#define ll long long
using namespace std;
const int n=4100;
int a[n][n],b[n][n];
int ap[n][10][260],bp[n][10];
int n,p,m;
int main()
}for(int i=0;i
}p=(p-1)/8+1;//矩陣b分成p塊
//預處理a矩陣,將其分塊,並將每一塊對應的256種情況預處理出來
//ap[i][j][k]:=將第i行第j快與對應的k所代表的的8位二進位制塊相乘所得的結果
for(int i=0;i}}
}//處理矩陣b,將其分塊,並將其每塊對應的二進位制串所對應的整數求出來
for(int i=0;i}}
//利用預處理出來的結果,將c[i][j]所對應的塊的相乘的值加起來
int ans=0,tmp;
for(int i=0;i
ans^=tmp;}}
printf("%d\n",ans);
}
牛客國慶集訓派對Day2
題意 給出最大4096 64和64 4096的矩陣,其中有乙個矩陣只含有0和1,問你它們相乘所得到得矩陣所有元素異或 思路 一開始我想到的是能不能將01矩陣的一排都用二進位制表示,但是發現2的64次方大於4096,反而增大了複雜度,於是沒有做出這題,題解是將矩陣分塊,最多分成8塊,這樣01矩陣的種數...
牛客國慶集訓派對Day2 Solution
a 矩陣乘法 思路 1 牛客機器太快了,暴力能過。1 include 2 using namespace std 34 define n 500056 intn,p,m 7int a n 100 b 100 n ans n n 89 void run 1029 30 31int main 32vie...
牛客國慶集訓派對Day1
a 看樣例過題 include include include include include using namespace std typedef long long ll typedef pairpii const int maxn 1e5 10 vectorg maxn int a 10 i...