暂无图片
暂无图片
暂无图片
暂无图片
暂无图片

[LeetCode] 1079. Letter Tile Possibilities 活字印刷

刷尽天下 2021-03-22
567

You have n
 tiles
, where each tile has one letter tiles[i]
 printed on it.

Return the number of possible non-empty sequences of letters you can make using the letters printed on those tiles
.

Example 1:

Input: tiles = "AAB"
Output: 8
Explanation: The possible sequences are "A", "B", "AA", "AB", "BA", "AAB", "ABA", "BAA".

Example 2:

Input: tiles = "AAABBC"
Output: 188

Example 3:

Input: tiles = "V"
Output: 1

Constraints:

1 <= tiles.length <= 7
tiles
 consists of uppercase English letters.


这道题给了一个字符串,让求出所有不同排列方式的非空子序列的个数。博主最开始做的时候以为是跟之前那道 Permutations II[1] 一样,是求有重复数字的全排列。但是这里求的不止是全排列,还有子序列的全排列,情况更多,不过好就好在不用返回所有的情况,而是返回总个数即可。这里还是需要用递归来做,由于可能存在大量的重复的字母,所以比较好的方法就是统计每个字母出现的次数,使用 HashMap 或者一个大小为 26 的数组。因为题目中限定了只有大写字母,所以用一个带大小为 26 的数组 cnt 更加省事。统计好了字母出现的次数之和,就可以对 cnt 数组调用递归了。在递归函数中,遍历每个字母,若其出现次数为0,则直接跳过。否则结果 res 自增1,因为加上一个当前字母就会形成一种新的排列方式。然后该字母的映射值减1,之后再对于更新后的 cnt 数组调用递归函数,将返回值加到结果 res 之中。之后要还原状态,即将当前的出现次数再加回1,参见代码如下:


class Solution {
public:
int numTilePossibilities(string tiles) {
vector<int> cnt(26);
for (char c : tiles) ++cnt[c - 'A'];
return helper(cnt);
}
int helper(vector<int>& cnt) {
int res = 0;
for (int i = 0; i < 26; ++i) {
if (cnt[i] == 0) continue;
++res;
--cnt[i];
res += helper(cnt);
++cnt[i];
}
return res;
}
};


Github 同步地址:

https://github.com/grandyang/leetcode/issues/1079


参考资料:

https://leetcode.com/problems/letter-tile-possibilities/

https://leetcode.com/problems/letter-tile-possibilities/discuss/308284/Concise-java-solution

https://leetcode.com/problems/letter-tile-possibilities/discuss/308398/C%2B%2B-Permutation-of-Combinations


LeetCode All in One 题目讲解汇总(持续更新中...)[2]

References

[1]
 Permutations II: http://www.cnblogs.com/grandyang/p/4359825.html
[2]
 LeetCode All in One 题目讲解汇总(持续更新中...): https://www.cnblogs.com/grandyang/p/4606334.html

文章转载自刷尽天下,如果涉嫌侵权,请发送邮件至:contact@modb.pro进行举报,并提供相关证据,一经查实,墨天轮将立刻删除相关内容。

评论