问题描述
公司购买了一块 m×nm×n 大小的地皮,需要将这块地皮规划为多个正方形区域。为了降低成本,要求划分的正方形区域个数尽量少。你需要帮助公司计算最少需要划分多少个正方形区域,才能完全覆盖这块地皮。
例如,对于一个 3×23×2 的地皮,最少可以划分为3个正方形区域;而对于一个 13×1113×11 的地皮,最少可以划分为6个正方形区域。
测试样例
样例1:
输入:
m = 3, n = 2
输出:3
样例2:
输入:
m = 13, n = 11
输出:6
样例3:
输入:
m = 4, n = 4
输出:1
#include <iostream>
#include <string>
#include <vector>
#include <climits>
#include <functional>
using namespace std;
int solution(int m, int n) {
// PLEASE DO NOT MODIFY THE FUNCTION SIGNATURE
// write code here
vector<vector<bool>> matrix(m + 1, vector<bool>(n + 1, false));
int ans = INT_MAX;
// Helper function to check if we can place a square of size len at position
// (row, col)
auto check = [&](int row, int col, int len) {
if (row + len - 1 > m || col + len - 1 > n)
return false;
for (int i = 0; i < len; i++) {
for (int j = 0; j < len; j++) {
if (matrix[row + i][col + j]) {
return false;
}
}
}
return true;
};
// Helper function to fill/unfill a square of size len at position (row, col)
auto fill = [&](int row, int col, int len) {
for (int i = 0; i < len; i++) {
for (int j = 0; j < len; j++) {
matrix[row + i][col + j] = !matrix[row + i][col + j];
}
}
};
// DFS function to try all possible square placements
function<void(int, int, int)> dfs = [&](int row, int col, int cnt) {
if (cnt >= ans)
return;
if (row > m) {
ans = cnt;
return;
}
if (col > n) {
dfs(row + 1, 1, cnt);
return;
}
bool flag = true;
for (int j = col; j <= n; j++) {
if (!matrix[row][j]) {
flag = false;
int maxSize = min(m - row + 1, n - j + 1);
for (int size = maxSize; size >= 1; size--) {
if (check(row, j, size)) {
fill(row, j, size);
dfs(row, j + size, cnt + 1);
fill(row, j, size); // backtrack
}
}
break;
}
}
if (flag) {
dfs(row + 1, 1, cnt);
}
};
dfs(1, 1, 0);
return ans;
}
int main() {
cout << (solution(3, 2) == 3) << endl;
cout << (solution(13, 11) == 6) << endl;
cout << (solution(4, 4) == 1) << endl;
}