力扣第314场周赛第四题-矩阵中和能被 K 整除的路径
6203. 矩阵中和能被 K 整除的路径
给你一个下标从 0 开始的 m × n 整数矩阵 grid 和一个整数 k 。你从起点 (0, 0) 出发,每一步只能往 下 或者往 右 ,你想要到达终点 (m - 1, n - 1) 。
请你返回路径和能被 k 整除的路径数目,由于答案可能很大,返回答案对 109 + 7 取余 的结果。
数据范围:
m == grid.length
n == grid[i].length
1 <= m, n <= 5 × 104
1 <= m × n <= 5 × 104
0 <= grid[i][j] <= 100
1 <= k <= 50
来源:力扣(LeetCode)
链接:https://leetcode.cn/problems/paths-in-matrix-whose-sum-is-divisible-by-k
思路:
动态规划,每个 grid[i][j] 拥有一个包含 k 个元素的路径数组 [0, ..., k-1],表示从 (0,0) 出发到达该点的路径和模 k分别余 0, 1, ..., k-1 的路径数目。
对于每个 grid[i][j] 其路径数组均可由 grid[i-1][j] 和 grid[i][j-1] 简单推导出来。
运行结果:
执行用时:252 ms, 内存消耗:55.1 MB, 通过测试用例:88 / 88
代码:
class Solution { private: long long dp[50005][50] = {0}; const int Mod = 1e9 + 7; int M, N; public: //杨辉三角求组合数C(n,k) int C(int n, int k){ k = min(n-k, k); if(k == 0)return 1; if(k == 1)return n; vector<int> ans(1, 1); for(int i = 1; i <= n; i++){ int tmp1 = ans[0], tmp2 = ans[1]; ans.push_back(0); for(int j = 1; j <= i; j++){ tmp2 = ans[j]; ans[j] += tmp1; if(ans[j] >= Mod)ans[j] -= Mod; tmp1 = tmp2; } } return ans[k]; } int numberOfPaths(vector<vector<int>>& grid, int k) { M = grid.size(); N = grid[0].size(); if(k == 1)return C(M+N-2, M-1); for(int i = 0; i < M; i++) for(int j = 0; j < N; j++) grid[i][j] %= k; dp[0][grid[0][0]] = 1; for(int i = 0; i < M; i++){ for(int j = 0; j < N; j++){ int tMp = grid[i][j], cc = i*N+j; for(int t = 0; t < k; t++){ int x = (t + tMp >= k)? t+tMp-k : t+tMp; if(i > 0)dp[cc][x] += dp[cc-N][t]; if(j > 0)dp[cc][x] += dp[cc-1][t]; dp[cc][x] %= Mod; } } } return (int)dp[M*N-1][0]; } };

浙公网安备 33010602011771号