【算法与数据结构】62、LeetCode不同路径

文章目录

  • 一、题目
  • 二、解法
    • 2.1 动态规划解法
    • 2.2 数论解法
  • 三、完整代码

所有的LeetCode题解索引,可以看这篇文章——【算法和数据结构】LeetCode题解。

一、题目

在这里插入图片描述

二、解法

2.1 动态规划解法

  思路分析:机器人只能向下或者向右移动,那么到达(i,j)位置的路径和(i-1,j)以及(i,j-1)有关。那么我们就得到的动态规划的表达式 d p [ i ] [ j ] = d p [ i − 1 ] [ j ] + d p [ i ] [ j − 1 ] dp[i][j]=dp[i-1][j]+dp[i][j-1] dp[i][j]=dp[i1][j]+dp[i][j1]。其中,因为到达第一行和第一列位置的路径只有一条,因此dp数组中第一行第一列的元素都为1。根据如上信息,我们写出如下代码。
  程序如下

class Solution {
public:
	int uniquePaths(int m, int n) {
		vector<vector<int>> dp(m, vector<int>(n, 1));
		for (int i = 1; i < m; i++) {
			for (int j = 1; j < n; j++) {
				dp[i][j] = dp[i - 1][j] + dp[i][j - 1];
			}
		}
		return dp[m - 1][n - 1];
	}
};

复杂度分析:

  • 时间复杂度: O ( m ∗ n ) O(m*n) O(mn)
  • 空间复杂度: O ( m ∗ n ) O(m*n) O(mn)

  上述代码还可以再空间上进行压缩。从二维数组的角度来看,(i,j)位置的路径数等于它上方的元素和左边的元素之和。如果省略掉上方的元素,我们就能用一个一维数组来表示dp数组。迭代公式为 d p [ i ] = d p [ i ] + d o p [ i − 1 ] dp[i] = dp[i]+dop[i-1] dp[i]=dp[i]+dop[i1],其中dop[i-1]代表左边元素,公式右边旧的dp[i]代表上方元素。最终输出为dp[n-1]。

class Solution {
public:
    int uniquePaths(int m, int n) {
        vector<int> dp(n);
        for (int i = 0; i < n; i++) dp[i] = 1;
        for (int j = 1; j < m; j++) {
            for (int i = 1; i < n; i++) {
                dp[i] += dp[i - 1];
            }
        }
        return dp[n - 1];
    }
};

复杂度分析:

  • 时间复杂度: O ( m ∗ n ) O(m*n) O(mn)
  • 空间复杂度: O ( n ) O(n) O(n)

2.2 数论解法

  思路分析:从数学上我们可以知道,要到达终点,每次又只能走一步,那么总共需要的步数是 m + n − 2 m+n-2 m+n2,那么有 m − 1 m-1 m1步是要往下走的,那么问题就变成了在 m + n − 2 m+n-2 m+n2步中, m − 1 m-1 m1步往下走有多少种组合。这是一个组合问题。因此,问题变成计算 C m + n − 2 m − 1 = ( m + n − 2 ) ! ( m − 1 ) ! ( n − 1 ) ! = ( m + n − 2 ) ∗ . . . ( n + 1 ) ∗ n ( m − 1 ) ! C_{m+n-2}^{m-1}=\frac{(m+n-2)!}{{(m-1)!}{(n-1)!}}=\frac{(m+n-2)*...(n+1)*n}{(m-1)!} Cm+n2m1=(m1)!(n1)!(m+n2)!=(m1)!(m+n2)...(n+1)n。结合上述讨论,我们写出如下代码。代码当中,为了防止乘积中分子溢出,我们首先使用long long类型,并在循环中不断除以分母。
  程序如下

class Solution {
public:
	int uniquePaths(int m, int n) {
		long long numerator = 1; // 分子
		int denominator = m - 1; // 分母
		int num1 = m - 1, num2 = m + n - 2;
		while (num1--) {
			numerator *= (num2--);
			while (denominator != 0 && numerator % denominator == 0) {	// 分母不能为0, 且分子要能整除分母
				numerator /= denominator;
				denominator--;
			}
		}
		return numerator;
	}
};

复杂度分析:

  • 时间复杂度: O ( m ) O(m) O(m)
  • 空间复杂度: O ( 1 ) O(1) O(1)

三、完整代码

# include <iostream>
# include <vector>
using namespace std;

// 62、不同路径I
class Solution {
public:
	int uniquePaths(int m, int n) {
		vector<vector<int>> dp(m, vector<int>(n, 1));
		for (int i = 1; i < m; i++) {
			for (int j = 1; j < n; j++) {
				dp[i][j] = dp[i - 1][j] + dp[i][j - 1];
			}
		}
		return dp[m - 1][n - 1];
	}
};

// 滚动数组削减空间复杂度
//class Solution {
//public:
//	int uniquePaths(int m, int n) {
//		vector<int> dp(n);
//		for (int i = 0; i < n; i++) dp[i] = 1;
//		for (int j = 1; j < m; j++) {
//			for (int i = 1; i < n; i++) {
//				dp[i] += dp[i - 1];
//			}
//		}
//		return dp[n - 1];
//	}
//};

// 数论方法
//class Solution {
//public:
//	int uniquePaths(int m, int n) {
//		long long numerator = 1; // 分子
//		int denominator = m - 1; // 分母
//		int num1 = m - 1, num2 = m + n - 2;
//		while (num1--) {
//			numerator *= (num2--);
//			while (denominator != 0 && numerator % denominator == 0) {	// 分母不能为0, 且分子要能整除分母
//				numerator /= denominator;
//				denominator--;
//			}
//		}
//		return numerator;
//	}
//};

int main() {
	int m = 3, n = 2;
	Solution s1;
	int result = s1.uniquePaths(m, n);
	cout << result << endl;
	system("pause");
	return 0;
}

end

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/315400.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

Komodor:Kubernetes 监控工具全面指南

为了方便起见&#xff0c;Komodor 提供了一个简单的 Web 界面&#xff0c;以帮助您监控 Kubernetes 集群的状态。它拥有付费和免费增值计划&#xff0c;除了在出现问题时通知用户外&#xff0c;还拥有一系列方便的工具&#xff0c;用于跟踪和管理集群中部署的资源的状态。让我们…

单片机I/O口驱动MOS管

自记录&#xff1a; 使用单片机做一个PLC,输出可如下两种情况&#xff1a; 单片机I/O口驱动&#xff0c;为什么一般都选用三极管而不是MOS管&#xff1f; 1.单片机的IO口&#xff0c;有一定的带负载能力。但电流很小&#xff0c;驱动能力有限&#xff0c;一般在10-20mA以内。…

【Java SE语法篇】6.数组

&#x1f4da;博客主页&#xff1a;爱敲代码的小杨. ✨专栏&#xff1a;《Java SE语法》 ❤️感谢大家点赞&#x1f44d;&#x1f3fb;收藏⭐评论✍&#x1f3fb;&#xff0c;您的三连就是我持续更新的动力❤️ 文章目录 1.数组的基本概念1.1 为什么使用数组&#xff1f;1.…

Realm Management Extension领域管理扩展之安全状态

RME基于Arm TrustZone技术。TrustZone技术在Armv6中引入,提供以下两个安全状态: 安全状态(Secure state)非安全状态(Non-secure state)以下图表显示了在AArch64中的这两个安全状态以及通常在每个安全状态中找到的软件组件: 该架构将在安全状态运行的软件与在非安全状态运…

【Linux实用篇】Linux常用命令(1)

目录 1.1 Linux命令初体验 1.1.1 常用命令演示 1.1.2 Linux命令使用技巧 1.1.3 Linux命令格式 1.2 文件目录操作命令 1.2.1 ls 1.2.2 cd 1.2.3 cat 1.2.4 more 1.2.5 tail 1.2.6 mkdir 1.2.7 rmdir 1.2.8 rm 1.1 Linux命令初体验 1.1.1 常用命令演示 在这一部分中…

C#,卡特兰数(Catalan number,明安图数)的算法源代码

一、概要 卡特兰数&#xff08;英语&#xff1a;Catalan number&#xff09;&#xff0c;又称卡塔兰数、明安图数&#xff0c;是组合数学中一种常出现于各种计数问题中的数列。以比利时的数学家欧仁查理卡特兰的名字来命名。1730年左右被蒙古族数学家明安图使用于对三角函数幂…

Linux 【C编程】IO进阶— 阻塞IO、非阻塞IO、 多路复用IO、 异步IO

文章目录 1.阻塞IO与非阻塞IO1.1为什么有阻塞式&#xff1f;1.2非阻塞 2.阻塞式IO的困境3.并发IO的解决方案3.1非阻塞式IO3.2多路复用IO3.2.1什么是多路复用IO&#xff1f;3.2.1多路复用IO select原理3.2.1多路复用IO poll原理 3.3异步IO 1.阻塞IO与非阻塞IO 1.1为什么有阻塞式…

国产麒麟系统开机没有网络需要点一下这个设置

问题描述&#xff1a; 一台国产电脑网线连接正常&#xff0c;打开网页后显示无法访问&#xff0c;那么是什么原因无法上网呢&#xff1f;下面就告诉你一个小方法去解决一下这个问题&#xff1b; 检查故障&#xff1a; 检测交换机、网线、水晶头全都正常&#xff0c;同房间摆放的…

ZooKeeper 实战(二) 命令行操作篇

文章目录 ZooKeeper 实战(二) 命令行操作篇1. 服务端命令1.1. 服务启动1.2. 查看服务1.3. 重启服务1.4. 停止服务 2. 客户端命令2.1. 启动客户端2.2. 查看节点信息查看根节点详情 ls -s /添加一个watch监视器 ls -w /列举出节点的级联节点 ls -R / 2.3. 查看节点状态2.4. 创建节…

Jenkins 问题

从gitlab 仓库拉去代码到Jenkins本地报错 ERROR: Couldn’t find any revision to build. Verify the repository and branch configuration for this job. 问题原因&#xff1a; 创建条目》配置的时候&#xff0c;gitlab仓库不存在master分支 修复后&#xff1a;

44-js return返回值,全局作用域,局部作用域,隐式作用域,变量的生命周期,delete释放内存

1.return返回值&#xff1a;函数执行后剩下结果就是返回值。 function fn(a,b,c){//return返回值return(abc);// console.log("aaa"); //return之后的值都不在执行了// alert("bbb"); //return之后的值不在执行了}console.log(fn(1,2,3)*10)…

人工智能:我的学习之旅与认知探索(第1版)

&#x1f31f;&#x1f30c; 欢迎来到知识与创意的殿堂 — 远见阁小民的世界&#xff01;&#x1f680; &#x1f31f;&#x1f9ed; 在这里&#xff0c;我们一起探索技术的奥秘&#xff0c;一起在知识的海洋中遨游。 &#x1f31f;&#x1f9ed; 在这里&#xff0c;每个错误都…

what is BERT?

BERT Introduction Paper 参考博客 9781838821593_ColorImages.pdf (packt-cdn.com) Bidirectional Encoder Representation from Transformer 来自Transformer的双向编码器表征 基于上下文&#xff08;context-based&#xff09;的嵌入模型。 那么基于上下文&#xff08;…

golang学习笔记——go语言多文件项目运行的四种方式

go语言多文件运行技巧 有两个源码文件的go语言项目如何运行? go.modmain.go Trie.go 如何直接运行go run main.go会提示找不到文件。 # 在windows10下运行 $ go run main.go # command-line-arguments .\main.go:6:9: undefined: Constructor是真的找不到文件吗。其实不是。…

一个成功的camera案例:ros2+gazebo+摄像头

各位看&#xff1a;随着大物体的移动&#xff0c;在涉嫌头的位置也发生了改变-----右上角那个/camera的位置也变了 右上角那个是摄像头图案&#xff0c;以下是仓库链接&#xff1a; ros-ign-gazebo-camera: https://github.com/arashsm79/ros-ign-gazebo-camera.git一个ros2摄…

基于多智能体点对点转换的分布式模型预测控制

matlab2020正常运行 基于多智能体点对点转换的分布式模型预测控制资源-CSDN文库

Zabbix“专家坐诊”第223期问答汇总

来源&#xff1a;乐维社区 问题一 Q&#xff1a;Zabbix 5.0安装完mysql之后怎么备份&#xff1f;忘记mysql当时创建的密码了&#xff0c;怎么样能查看设置的密码&#xff1f; A&#xff1a;mysql初始化密码在 /var/log/mysqld.log中可以看到&#xff0c;搜关键字temporary pas…

膜结构球形影院为观众打造观影新体验

在数字科技快速发展的当下&#xff0c;轻空间公司打破传统影院的束缚&#xff0c;领航未来娱乐体验的创新浪潮。膜结构球形影院问世&#xff0c;它不仅仅是一个娱乐场所&#xff0c;更是一场極致沉浸感的感官之旅&#xff0c;为观众带来震撼性的视听冲击。 沉浸式体验的新纪元 …

Jenkins安装和配置

拉取Jenkins镜像 docker pull jenkins/jenkins 编写jenkins_docker.yml version: "3.1" services:jenkins:image: jenkins/jenkinscontainer_name: jenkinsports:- 8080:8080- 50000:50000volumes:- ./data/:/var/jenkins_home/首次启动会因为数据卷data目录没有权限…

Nginx配置负载均衡实例

Nginx配置反向代理实例二 提醒一下&#xff1a;下面实例讲解是在Mac系统演示的&#xff1b; 负载均衡实例实现的效果 浏览器地址栏输入地址http://192.168.0.101/test/a.html&#xff0c;刷新页面进行多次请求&#xff0c;负载均衡效果&#xff0c;平均分配到8080端口服务和8…