class Solution {
int m, n, k;
boolean[][] visited;
public int movingCount(int m, int n, int k) {
this.m = m;
this.n = n;
this.k = k;
this.visited = new boolean[m][n];
return dfs(0, 0, 0, 0);
}
public int dfs(int i, int j, int si, int sj) {
//深度优先回溯
if (i >= m || j >= n || k < si + sj || visited[i][j]) return 0;
visited[i][j] = true;
return 1 + dfs(i + 1, j, (i + 1) % 10 != 0 ? si + 1 : si - 8, sj) +
dfs(i, j + 1, si, (j + 1) % 10 !=0 ? sj + 1 : sj - 8);
}
}
//未剪枝
class Solution {
int maxn = 0;
boolean[][] vis;
int[][] dir = new int[][]{{1,0},{-1,0},{0,1},{0,-1}};
public int sumNums(int num)
{
int sum = 0;
while(num > 0)
{
sum += num % 10;
num /= 10;
}
return sum;
}
public int movingCount(int m, int n, int k) {
if(m == 0)
return 0;
vis = new boolean[m][n];
for(int i=0;i<m;i++)
for(int j=0;j<n;j++)
vis[i][j] = false;
dfs(0,0,m,n,k);
for(int i=0;i<m;i++)
for(int j=0;j<n;j++)
{
if(vis[i][j])
maxn++;
}
return maxn;
}
void dfs(int x,int y,int m,int n,int k)
{
vis[x][y] = true;
for(int j=0;j<4;j++)
{
int ux = x + dir[j][0];
int uy = y + dir[j][1];
if(ux < 0 || ux >= m || uy >= n || uy < 0 || sumNums(ux)+sumNums(uy) > k)
continue;
if(vis[ux][uy])
continue;
dfs(ux,uy,m,n,k);
}
}
}
class Solution {
public:
int res = 0;
int dx[4] = {-1, 0, 1, 0};
int dy[4] = {0, 1, 0, -1};
int movingCount(int m, int n, int k) {
vector<vector> visited(m, vector(n, false));
dfs(m, n, k, 0, 0, visited);
return res;
}
void dfs(int m, int n, int k, int i, int j, vector<vector<bool>>& visited){
if(i >= m||i < 0||j < 0||j >= n||add(i,j) > k||visited[i][j]) return;
//做选择
visited[i][j] = true;
res++;
//继续深入
for(int p = 0; p < 4; p++){
int x = i + dx[p];
int y = j + dy[p];
dfs(m, n, k, x, y, visited);
}
}
int add(int i, int j){
int sum = 0;
while(i != 0){
sum += i % 10;
i /= 10;
}
while(j != 0){
sum += j % 10;
j /= 10;
}
return sum;
}
c++代码 DFS
class Solution { //本题的思路为递归法
public:
int cal(int i,int j,int k){ //先写个计算位数和的函数cal
int sum = 0;
while(i){
sum+=i%10;
i/=10;
}
while(j)
{
sum+=j%10;
j/=10;
}
if(sum<=k)
return true;
else
return false;
}
int result = 0;
int a[101][101]={0} ;
void traversal(int i, int j, int m, int n, int k){ //注意递归传入的参数有点多,顺序不要乱。result和visited必须要有&引用符号
if(i<0||j<0||i>=m||j>=n||!cal(i,j,k) ||a[i][j]) return; //递归终止条件,也就是走到了不符合条件的格子:1.超出边界 2.位数和大于k 3.格子已经被访问过
a[i][j] = 1; //该格子符合条件,标记为true
result++; //结果+1
traversal(i+1, j, m, n, k); //按照四个方向进行递归
traversal(i-1, j, m, n, k);
traversal(i, j+1, m, n, k);
traversal(i, j-1, m, n, k);
}
int movingCount(int m, int n, int k) {
//初始化result
//初始化visited标记矩阵
traversal(0, 0, m, n, k);
return result;
}
class Solution {
int m;
int n;
int k;
boolean[][] visited;
public int movingCount(int m, int n, int k) {
this.m = m;
this.n = n;
this.k = k;
visited = new boolean[m][n];
return dfs(0,0);
}
int dfs(int i, int j){
//是否在方格之内或者是否访问过或者是否是障碍物
if(i < 0 || j < 0|| i >= m || j >= n|| visited[i][j] || k < sum(i) + sum(j)){
return 0;
}
visited[i][j] = true;
return 1 + dfs(i + 1, j) + dfs(i, j + 1);
}
int sum(int x){
int res = 0;
while(x != 0){
res = res + x % 10;
x = x / 10;
}
return res;
//时间复杂度:O(mn)
//空间复杂度:O(mn)
}
}
class Solution {
public int[] dx = {-1,0,1,0};
public int[] dy = {0,1,0,-1};
public int movingCount(int m, int n, int k) {
boolean[][] map = new boolean[m][n];
int res = dfs(map,0,0,k);
return res;
}
public int dfs(boolean[][] map, int x, int y, int k) {
if(x<0||x>=map.length||y<0||y>=map[0].length||shuweihe(x)+shuweihe(y)>k||map[x][y]==true) {
return 0;
}
map[x][y] = true;
return 1+dfs(map,x+1,y,k)+dfs(map,x-1,y,k)+dfs(map,x,y-1,k)+dfs(map,x,y+1,k);
}
public int shuweihe(int num) {
int sum=0;
while(num>0) {
sum+=num%10;
num = num/10;
}
return sum;
}
}
”’java
class Solution {
public int movingCount(int m, int n, int k) {
//如果一个格子不可达,那么也不能从该格子到达其他格子
//一个格子是否可达,和他周围的格子相关
if(k 0){
return 1;
}
boolean[][] vis = new boolean[m][n];
int ans = 1;
vis[0][0] = true;
for(int i = 0;i < m;i++){
for(int j = 0;j < n;j++){
if((i 0 && j 0) || sumT(i) + sumT(j) > k){
continue;
}
if(i 0){
vis[i][j] = vis[i][j-1];
}else if(j 0){
vis[i][j] = vis[i-1][j];
}else{
if(vis[i-1][j] || vis[i][j-1]){
vis[i][j] = true;
}
}
ans += vis[i][j] ? 1:0;
}
}
return ans;
}
//求一个整数的数位之和
public int sumT(int m){
int sum = 0;
while(m != 0){
int res = m % 10;
sum += res;
m = m/10;
}
return sum;
}
class Solution {
int res = 0;
public int movingCount(int m, int n, int k) {
boolean[][] visited = new boolean[m][n];
backTracking(0,0,m,n,k,visited);
return res;
}
public void backTracking(int x, int y, int m, int n, int k,boolean[][] visited) {
// 边界
if(x < 0 || y < 0 || x >= m || y >= n || visited[x][y] == true) return;
int sum = bitSum(x) + bitSum(y);
if(sum > k) return;
// 逻辑
visited[x][y] = true;
res ++;
// 回溯
backTracking(x+1,y,m,n,k,visited);
backTracking(x,y+1,m,n,k,visited);
}
//求数位之和
public int bitSum (int num) {
int sum = 0;
while(num > 0) {
sum += num % 10;
num /= 10;
}
return sum;
}
}
class Solution {
int m, n, k;
boolean[][] visited;
public int movingCount(int m, int n, int k) {
//坐标的数位之和<=k
this.m = m;
this.n = n;
this.k = k;
this.visited = new boolean[m][n];
return dfs(0, 0, 0, 0);
}
public int dfs(int i, int j, int si, int sj){
if(i >=m || j >= n || si + sj > k || visited[i][j])
return 0;
visited[i][j] = true;
return 1 + dfs(i + 1, j, (i + 1) % 10 != 0? si + 1 : si - 8, sj)
+ dfs(i, j + 1, si, (j + 1) % 10 != 0? sj + 1 : sj - 8);
}
}
class Solution {
int count;
boolean[][] record;//记录已经遍历过的点
public int movingCount(int m, int n, int k) {
record = new boolean[m][n];
dfs(0, 0, m, n, k);
return count;
}
public void dfs(int i, int j, int m, int n, int k){
if(i < 0 || j < 0 || i >= m || j >= n){
return;
}
if(getSum(i, j) > k || record[i][j] == true){
return;
}
count += 1;
record[i][j] = true;
dfs(i - 1, j, m, n, k);
dfs(i + 1, j, m, n, k);
dfs(i, j - 1, m, n, k);
dfs(i, j + 1, m, n, k);
}
private int getSum(int i, int j){
int sum = 0;
while(i > 0){
sum += i % 10;
i = i / 10;
}
while(j > 0){
sum += j % 10;
j = j / 10;
}
return sum;
}
}
共以下 15 个回答
class Solution {> visited(m, vector (n, false));
public:
int res = 0;
int dx[4] = {-1, 0, 1, 0};
int dy[4] = {0, 1, 0, -1};
int movingCount(int m, int n, int k) {
vector<vector
dfs(m, n, k, 0, 0, visited);
return res;
}
};
效率太低了
c++代码 DFS
class Solution { //本题的思路为递归法
public:
int cal(int i,int j,int k){ //先写个计算位数和的函数cal
int sum = 0;
while(i){
sum+=i%10;
i/=10;
}
while(j)
{
sum+=j%10;
j/=10;
}
if(sum<=k)
return true;
else
return false;
};
dfs做
时间复杂度:O(mn)
空间复杂度:O(mn)
”’java
class Solution {
public int movingCount(int m, int n, int k) {
//如果一个格子不可达,那么也不能从该格子到达其他格子
//一个格子是否可达,和他周围的格子相关
if(k 0){
return 1;
}
boolean[][] vis = new boolean[m][n];
int ans = 1;
vis[0][0] = true;
for(int i = 0;i < m;i++){
for(int j = 0;j < n;j++){
if((i 0 && j 0) || sumT(i) + sumT(j) > k){
continue;
}
if(i 0){
vis[i][j] = vis[i][j-1];
}else if(j 0){
vis[i][j] = vis[i-1][j];
}else{
if(vis[i-1][j] || vis[i][j-1]){
vis[i][j] = true;
}
}
}
”’
class Solution {
boolean jude[][];
int count = 0;
int a;
int b;
public int movingCount(int m, int n, int k) {
// mn<100 从头开始 上下左右
jude=new boolean[m][n];
a=m;
b=n;
backing(0,0,k);
return count;
}
public void backing(int i,int j,int k)
{
if(i<0||i>=a||j<0||j>=b||jude[i][j])
{
return;
}
if((i/10+i%10+j/10+j%10)>k)
{
return ;
}
count++;
jude[i][j]=true;//走过了 永久标记
backing(i+1,j,k);
backing(i-1,j,k);
backing(i,j+1,k);
backing(i,j-1,k);
}
8.2
Day24:下面是代码