216.组合总和III

卡哥建议:如果把 组合问题理解了,本题就容易一些了。

题目链接/文章讲解:https://programmercarl.com/0216.%E7%BB%84%E5%90%88%E6%80%BB%E5%92%8CIII.html

    视频讲解:https://www.bilibili.com/video/BV1wg411873x

做题思路:

本题k相当于树的深度,9(因为整个集合就是9个数)就是树的宽度。

例如 k = 2,n = 4的话,就是在集合[1,2,3,4,5,6,7,8,9]中求 k(个数) = 2, n(和) = 4的组合。

选取过程如图:

图中,可以看出,只有最后取到集合(1,3)和为4 符合条件。

回溯三部曲看卡哥文章吧。

剪枝优化:

1,已选元素总和如果已经大于n(图中数值为4)了,那么往后遍历就没有意义了,直接剪掉。

2,for循环的范围也可以剪枝,i <= 9 - (k - path.size()) + 1就可以了,和昨天的题一样

本题代码:

 1 class Solution {
2 private:
3 vector<vector<int>> result; // 存放结果集
4 vector<int> path; // 符合条件的结果
5 void backtracking(int targetSum, int k, int sum, int startIndex) {
6 if (sum > targetSum) { // 剪枝操作
7 return; // 如果path.size() == k 但sum != targetSum 直接返回
8 }
9 if (path.size() == k) {
10 if (sum == targetSum) result.push_back(path);
11 return;
12 }
13 for (int i = startIndex; i <= 9 - (k - path.size()) + 1; i++) { // 剪枝
14 sum += i; // 处理
15 path.push_back(i); // 处理
16 backtracking(targetSum, k, sum, i + 1); // 注意i+1调整startIndex
17 sum -= i; // 回溯
18 path.pop_back(); // 回溯
19 }
20 }
21
22 public:
23 vector<vector<int>> combinationSum3(int k, int n) {
24 result.clear(); // 可以不加
25 path.clear(); // 可以不加
26 backtracking(n, k, 0, 1);
27 return result;
28 }
29 };

17.电话号码的字母组合

卡哥建议:本题大家刚开始做会有点难度,先自己思考20min,没思路就直接看题解。

题目链接/文章讲解:https://programmercarl.com/0017.%E7%94%B5%E8%AF%9D%E5%8F%B7%E7%A0%81%E7%9A%84%E5%AD%97%E6%AF%8D%E7%BB%84%E5%90%88.html

    视频讲解:https://www.bilibili.com/video/BV1yV4y1V7Ug

做题思路:

电话按键上2~9数字上对应着3个或4个字母,题目求的是输入数字,输出字母的组合,可以使用map或者定义一个二维数组,例如:string letterMap[10][],来做映射,10行,4列的二维数组,代码见卡哥文章。

图中可以看出遍历的深度,就是输入"23"的长度,而叶子节点就是我们要收集的结果,输出["ad", "ae", "af", "bd", "be", "bf", "cd", "ce", "cf"]。

   需要一个字符串s来收集叶子节点的结果,然后用一个字符串数组result保存起来,   
   代码中的 index 是从0开始的,是记录遍历第几个数字了,就是用来遍历digits的(题目中给出数字字符串“23”),就是下标,同时index也表示树的深度。 

本题代码:

 1 class Solution {
2 private:
3 const string letterMap[10] = { //二维数组,10行,列并没有定义,但能看出来
4 "", // 0
5 "", // 1
6 "abc", // 2
7 "def", // 3
8 "ghi", // 4
9 "jkl", // 5
10 "mno", // 6
11 "pqrs", // 7
12 "tuv", // 8
13 "wxyz", // 9
14 };
15 public:
16 vector<string> result;//放叶子节点的结果
17 string s;
18 void backtracking(const string& digits, int index) {
19 if (index == digits.size()) {
20 result.push_back(s);
21 return;
22 }
23 int digit = digits[index] - '0'; // 将index指向的数字转为int,比如digits[0]="2",减完后,就是2了
24 string letters = letterMap[digit]; // 取数字对应的字符集,比如,letterMap[2]="abc",然后在二维数组里就能找到对应的字符串
25 for (int i = 0; i < letters.size(); i++) { //树的结构,看上图
26 s.push_back(letters[i]); // 处理
27 backtracking(digits, index + 1); // 递归,注意index+1,一下层要处理下一个数字了
28 s.pop_back(); // 回溯
29 }
30 }
31 vector<string> letterCombinations(string digits) {
32 s.clear();
33 result.clear();
34 if (digits.size() == 0) {
35 return result;
36 }
37 backtracking(digits, 0);
38 return result;
39 }
40 };

代码随想录算法训练营第二十五天| 216.组合总和III 17.电话号码的字母组合的更多相关文章

  1. 代码随想录算法训练营第二天| 977.有序数组的平方 ,209.长度最小的子数组 ,59.螺旋矩阵II

    977.有序数组的平方 :https://leetcode.cn/problems/squares-of-a-sorted-array/ 心得:周末再写... public class Solutio ...

  2. 代码随想录算法训练营day01 | leetcode 704/27

    前言   考研结束半个月了,自己也简单休整了一波,估了一下分,应该能进复试,但还是感觉不够托底.不管怎样,要把代码能力和八股捡起来了,正好看到卡哥有这个算法训练营,遂果断参加,为机试和日后求职打下一个 ...

  3. 代码随想录算法训练营day02 | leetcode 977/209/59

    leetcode 977   分析1.0:   要求对平方后的int排序,而给定数组中元素可正可负,一开始有思维误区,觉得最小值一定在0左右徘徊,但数据可能并不包含0:遂继续思考,发现元素分布有三种情 ...

  4. 代码随想录算法训练营day06 | leetcode 242、349 、202、1

    基础知识 哈希 常见的结构(不要忘记数组) 数组 set (集合) map(映射) 注意 哈希冲突 哈希函数 LeetCode 242 分析1.0 HashMap<Character, Inte ...

  5. 代码随想录算法训练营day03 | LeetCode 203/707/206

    基础知识 数据结构初始化 // 链表节点定义 public class ListNode { // 结点的值 int val; // 下一个结点 ListNode next; // 节点的构造函数(无 ...

  6. 代码随想录算法训练营day22 | leetcode 235. 二叉搜索树的最近公共祖先 ● 701.二叉搜索树中的插入操作 ● 450.删除二叉搜索树中的节点

    LeetCode 235. 二叉搜索树的最近公共祖先 分析1.0  二叉搜索树根节点元素值大小介于子树之间,所以只要找到第一个介于他俩之间的节点就行 class Solution { public T ...

  7. 代码随想录算法训练营day18 | leetcode 513.找树左下角的值 ● 112. 路径总和 113.路径总和ii ● 106.从中序与后序遍历序列构造二叉树

    LeetCode 513.找树左下角的值 分析1.0 二叉树的 最底层 最左边 节点的值,层序遍历获取最后一层首个节点值,记录每一层的首个节点,当没有下一层时,返回这个节点 class Solutio ...

  8. 代码随想录算法训练营day17 | leetcode ● 110.平衡二叉树 ● 257. 二叉树的所有路径 ● 404.左叶子之和

    LeetCode 110.平衡二叉树 分析1.0 求左子树高度和右子树高度,若高度差>1,则返回false,所以我递归了两遍 class Solution { public boolean is ...

  9. 代码随想录算法训练营day16 | leetcode ● 104.二叉树的最大深度 559.n叉树的最大深度 ● 111.二叉树的最小深度 ● 222.完全二叉树的节点个数

    基础知识 二叉树的多种遍历方式,每种遍历方式各有其特点 LeetCode 104.二叉树的最大深度 分析1.0 往下遍历深度++,往上回溯深度-- class Solution { int deep ...

  10. 代码随想录算法训练营day13

    基础知识 二叉树基础知识 二叉树多考察完全二叉树.满二叉树,可以分为链式存储和数组存储,父子兄弟访问方式也有所不同,遍历也分为了前中后序遍历和层次遍历 Java定义 public class Tree ...

随机推荐

  1. 多线程合集(三)---异步的那些事之自定义AsyncTaskMethodBuilder

    引言 之前在上一篇文章中多线程合集(二)---异步的那些事,async和await原理抛析,我们从源码去分析了async和await如何运行,以及将编译后的IL代码写成了c#代码,以及实现自定义的Aw ...

  2. 「高频面试题」Redis的持久化方式有哪些?

    RDB RDB(Redis DataBase)持久化是把当前Redis中全部数据生成快照保存在硬盘上.RDB持久化可以手动触发,也可以自动触发.save和bgsave命令都可以手动触发RDB持久化.除 ...

  3. 在SQL中将特定的数据始终排在第一行

    将特定的数据始终排在第一行 第一种方式: select * from ( select Id,1 num from InquiryPurchaseProduct where Id = 50 union ...

  4. [Qt开发]一口气搞懂串口通信

    好多小鳄鱼 一.关于串口通信: Qt的确有自己的串口通信类,就是QSerialPort,但是我们在使用过程中因为要更加定制化的使用串口通信类减小开发的难度,所以我们会提供一个串口通信类,也就是这个Se ...

  5. JUC同步锁原理源码解析四----Semaphore

    JUC同步锁原理源码解析四----Semaphore Semaphore 1.Semaphore的来源 A counting semaphore. Conceptually, a semaphore ...

  6. 2023-06-22:一所学校里有一些班级,每个班级里有一些学生,现在每个班都会进行一场期末考试 给你一个二维数组 classes ,其中 classes[i] = [passi, totali] 表

    2023-06-22:一所学校里有一些班级,每个班级里有一些学生,现在每个班都会进行一场期末考试 给你一个二维数组 classes ,其中 classes[i] = [passi, totali] 表 ...

  7. 手机号码吉利数PHP检测算法代码,超级实用

    手机号码吉利数理预测解读:将手机号码末尾的四个数字,先除以八十,再减去整数部分,只使用剩下的小数(小数点反面的数字)乘以八十,然后将所得结果,对表查阅,就知道吉凶.(换句话说就是余数)例如:手机尾号是 ...

  8. Java版人脸跟踪三部曲之三:编码实战

    欢迎访问我的GitHub 这里分类和汇总了欣宸的全部原创(含配套源码):https://github.com/zq2599/blog_demos 本篇概览 作为<Java版人脸跟踪三部曲> ...

  9. 从钢铁行业数字化管控与超自动化融合,看华为WeAutomate能力进化

    文/王吉伟 钢铁行业的数字化转型,历来都是值得探讨的热点话题. 2022年,我国粗钢产量10.13亿吨,占据了全球钢铁供给市场的半壁江山. 这组数据可谓非常抢眼,但仍旧难掩诸多企业的各种经营问题. 钢 ...

  10. jar包、war包项目部署

    部署 部署 jar包 部署 war包 部署 jar包 环境准备 JDK Tomcat Linux 环境 1.将jar文件上传至服务器 2.编写脚本 启动脚本放在跟jar 一起的路径下,如果不放在同一路 ...