一开始看到这个题的时候,我还在想有没有什么简单做法,像动态规划或者堆排序什么的避免超时,结果一直没什么思路。直到我看懂了提示:
1
≤
m
,
n
≤
8
1 \leq m, n \leq 8
1≤m,n≤8, 即
m
,
n
m, n
m,n 都在
[
1
,
8
]
[1, 8]
[1,8] 之间,并不是只有
n
n
n 小于8, 那这样就可以直接用暴力做了。
做法类似 leetcode 里面的全排列的那个题,利用 dfs 递归找到所有可能的排列,并计算每一种方案的得分记录最大值。可以提前建一张 m × m m\times m m×m 的表记录每个老师和学生之间默契,来简化后期的计算,降低时间复杂度。
附上代码:
class Solution {
int Score = 0;
map<int,int> visited;
vector<vector<int> > mapping = vector<vector<int> >(9, vector<int>(9, 0));
int get_score(vector<int>& v1, vector<int>& v2){
int score = 0;
for(int i=0; i<v1.size(); i++) {
if(v1[i] == v2[i]) score++;
}
return score;
}
int plan_calculate(int plan) {
int out = 0;
int cnt = 1;
while(plan > 0) {
out += mapping[cnt][plan%10];
cnt++;
plan /= 10;
}
return out;
}
void get_poss(int x, int m){
if(x / (int)pow(10, m-1) > 0) {
Score = max(Score, plan_calculate(x));
return ;
} else {
for(int i = 1; i <= m; i++) {
if(visited.count(i) == 0) visited[i] = 1;
else if(visited[i] == 0) visited[i] = 1;
else continue;
get_poss(x*10 + i, m);
visited[i] = 0;
}
}
return ;
}
public:
int maxCompatibilitySum(vector<vector<int>>& students, vector<vector<int>>& mentors) {
int m = students.size(), n = students[0].size();
for(int i = 1; i <= m; i++ ) {
for(int j = 1; j <= m; j++){
mapping[i][j] = get_score(students[i-1], mentors[j-1]);
}
}
get_poss(0, m);
return Score;
}
};