问题描述
这是 LeetCode 问题 17:
给定一个包含 2-9 位数字的字符串,返回该数字可以表示的所有可能的字母组合。以任意顺序返回答案。
(https://leetcode.com/problems/letter-combinations-of-a-phone-number/)
以下是我的 DFS 递归代码:
class Solution {
public static final String[] map = {"","","abc","def","ghi","jkl","mno","pqrs","tuv","wxyz"};
public List<String> letterCombinations(String digits){
List<String> result = new ArrayList<String>();
if(digits == null || digits.length() == 0){return result;}
int curr_index = 0;
StringBuilder prefix = new StringBuilder("");
update_result(digits,prefix,curr_index,result);
return result;
}
private void update_result(String digits,StringBuilder prefix,int curr_index,List<String> result){
if(curr_index >= digits.length()){
result.add(prefix.toString());
return;
}
else{
String letters = map[ digits.charat(curr_index) - '0' ];
for(int i = 0; i < letters.length(); i++){
prefix.append( letters.charat(i) );
update_result(digits,curr_index+1,result);
prefix.deleteCharat(prefix.length() -1);
}
return;
}
}
}
在 LeetCode 解决方案中,它说时间复杂度为 O(n*n^4),其中 n 是输入的长度。除了 n^4 之外,我无法理解剩余的额外 n 来自哪里。
我对代码的分析是:T(n) = O(1) + 4T(n-1)。 (for 循环重复了 4 次,长度减 1。并且在循环中更新前缀 String 需要恒定的时间。)
它解决了 1 + 4 + 4^1+ ... + 4^n = O(4^n)
谁能帮忙解释为什么解决方案说时间复杂度是 O(n*4^n)?
解决方法
我同意你的看法,时间复杂度应该是 O(4^n)。
我有几个想法为什么它可以是 O(n * 4^n):
StringBuilder 的 append 方法在其容量达到阈值时可能需要 O(n) 时间,这意味着将所有元素复制到新数组中。但是在您的情况下,结果字符串的最大长度为 4(来自问题约束),而阈值的默认值为 16(https://docs.oracle.com/javase/8/docs/api/java/lang/StringBuilder.html#StringBuilder-java.lang.String-)。由于 4
-
StringBuilder 的 deleteCharAt 方法在最坏的情况下需要 O(n) 时间,因为数组复制。但是在您的情况下,您只删除了最后一个字符,这需要 O(1) 时间。
-
使用 String 而不是 StringBuilder,其中一个元素的连接和删除需要 O(n) 时间