【Leetcode】1444. Number of Ways of Cutting a Pizza
admin
2024-02-11 03:26:03

题目地址:

https://leetcode.com/problems/number-of-ways-of-cutting-a-pizza/

给定一个m×nm\times nm×n字符矩阵,只含'A''.'。要求将其切成kkk块(即切k−1k-1k−1刀)。每次可以横着切一刀或者竖着切一刀,要求切出的那一块必须含'A'。问有多少种不同的切分方式。

思路是记忆化搜索。设f[x][y][c]f[x][y][c]f[x][y][c]是从(x,y)(x, y)(x,y)到(m−1,n−1)(m-1,n-1)(m−1,n−1)这一部分的不同切分方式。那么我们就是要求f[0][0][k−1]f[0][0][k-1]f[0][0][k−1]。可以直接枚举第一刀是怎么切的,然后递归处理即可。为了快速判断某个子矩阵是否含'A',我们可以用一个前缀和数组预处理一下。代码如下:

class Solution {public:vector> pre;int MOD = 1e9 + 7;int ways(vector& ps, int k) {int m = ps.size(), n = ps[0].size();pre = vector>(m + 1, vector(n + 1, 0));for (int i = 1; i <= m; i++)for (int j = 1; j <= n; j++)pre[i][j] = (ps[i - 1][j - 1] == 'A' ? 1 : 0) + pre[i - 1][j] +pre[i][j - 1] - pre[i - 1][j - 1];vector>> f(m, vector>(n, vector(k, -1)));return dfs(0, 0, m, n, k - 1, f);}int dfs(int x, int y, int m, int n, int k, vector>>& f) {if (x == m || y == n) return 0;if (~f[x][y][k]) return f[x][y][k];if (!k) return f[x][y][k] = check(x, y, m - 1, n - 1) ? 1 : 0;int res = 0;for (int i = x; i < m; i++)if (check(x, y, i, n - 1))res = (res + dfs(i + 1, y, m, n, k - 1, f)) % MOD;for (int j = y; j < n; j++)if (check(x, y, m - 1, j))res = (res + dfs(x, j + 1, m, n, k - 1, f)) % MOD;return f[x][y][k] = res;}bool check(int x1, int y1, int x2, int y2) {return pre[x2 + 1][y2 + 1] - pre[x1][y2 + 1] - pre[x2 + 1][y1] +pre[x1][y1] > 0;}
};

时空复杂度O(mnk)O(mnk)O(mnk)。

相关内容

热门资讯

从哈尔滨到长白山闺蜜5天4晚天... 从哈尔滨到长白山闺蜜5天4晚天池+延吉边境:拍照打卡真实体验 一、出发前的纠结:比老板还难搞的攻略,...
搭上低空经济、AI文旅?两连板... 来源:e公司 桂林旅游(000978)回应市场热点。 9月8日,桂林旅游再度涨停,斩获2连板。当天晚...
八达岭长城国庆怎么去最省心?坐... 八达岭长城是来北京必去的景点之一,尤其是第一次来北京的游客。但国庆期间去八达岭,最大的挑战不是爬长城...
秋日睦邻游园会热闹开锣!居民重... (来源:上观新闻) 近日,殷行街道包头路社区睦邻活动室里,举办了一场秋日睦邻趣味游园会,辖区居民、户...
带父母去长白山怎么玩?3天2晚... 带父母去长白山怎么玩?3天2晚天池攻略,有些坑帮你们踩过了 一句话总结:这次带父母去长白山,我选了黑...