题目描述
你有一套活字字模 tiles,其中每个字模上都刻有一个字母 tiles[i]。返回你可以印出的非空字母序列的数目。
示例:
输入:“AAB”
输出:8
解释:可能的序列为 “A”, “B”, “AA”, “AB”, “BA”, “AAB”, “ABA”, “BAA”。
总结
SC 回溯的题有些用数学是投机取巧,但有些不是,是6
SC2 就是抽象出来,不在乎实际排列出来是什么字符串,而是 计数 判断
Sample Code 1 (不理解)
class Solution {
public int numTilePossibilities(String tiles) {
char[] chars = tiles.toCharArray();
Arrays.sort(chars);
return helper(0, 1, 1, 1, new int[26], chars);
}
private int helper(int start, int a, int b, int m, int[] counts, char[] chars) {
int result = 0;
a *= m;
for (int i = start; i < chars.length; i++) {
int c_index = chars[i] - 'A';
if (i == start || chars[i] != chars[i - 1]) {
b *= (++counts[c_index]);
result += a / b + helper(i + 1, a, b, m+1, counts, chars);
b /= (counts[c_index]--);
}
}
return result;
}
}
Sample Code 2
class Solution {
public int numTilePossibilities(String tiles) {
int[] record = new int[26];
for (char c : tiles.toCharArray()) {
record[c - 'A']++;
}
return dfs(record);
}
private int dfs(int[] record) {
int sum = 0;
for (int i = 0; i < 26; i++) {
if (record[i] == 0) continue;
record[i]--;
sum++;
sum += dfs(record);
record[i]++;
}
return sum;
}
}
Demo Code
class Solution {
List<String> list = new ArrayList<>();
public int numTilePossibilities(String tiles) {
boolean[] visited = new boolean[tiles.length()+1];
find(new StringBuilder(), visited, tiles);
return list.size();
}
private void find(StringBuilder temp, boolean[] visited, String tiles) {
if(temp.length() >= tiles.length()) {
return;
}
for(int i = 0; i < tiles.length(); i++) {
if(visited[i] == false) {
temp.append(tiles.substring(i, i+1));
visited[i] = true;
if(!list.contains(temp.toString())) {
list.add(temp.toString());
find(temp, visited, tiles);
}
temp.delete(temp.length()-1, temp.length());
visited[i] = false;
}
}
}
}
来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/letter-tile-possibilities