目标
你是一位系统管理员,手里有一份文件夹列表 folder,你的任务是要删除该列表中的所有 子文件夹,并以 任意顺序 返回剩下的文件夹。
如果文件夹 folder[i] 位于另一个文件夹 folder[j] 下,那么 folder[i] 就是 folder[j] 的 子文件夹 。folder[j] 的子文件夹必须以 folder[j] 开头,后跟一个 "/"。例如,"/a/b" 是 "/a" 的一个子文件夹,但 "/b" 不是 "/a/b/c" 的一个子文件夹。
文件夹的「路径」是由一个或多个按以下格式串联形成的字符串:'/' 后跟一个或者多个小写英文字母。
- 例如,"/leetcode" 和 "/leetcode/problems" 都是有效的路径,而空字符串和 "/" 不是。
示例 1:
输入:folder = ["/a","/a/b","/c/d","/c/d/e","/c/f"]
输出:["/a","/c/d","/c/f"]
解释:"/a/b" 是 "/a" 的子文件夹,而 "/c/d/e" 是 "/c/d" 的子文件夹。
示例 2:
输入:folder = ["/a","/a/b/c","/a/b/d"]
输出:["/a"]
解释:文件夹 "/a/b/c" 和 "/a/b/d" 都会被删除,因为它们都是 "/a" 的子文件夹。
示例 3:
输入: folder = ["/a/b/c","/a/b/ca","/a/b/d"]
输出: ["/a/b/c","/a/b/ca","/a/b/d"]
说明:
- 1 <= folder.length <= 4 * 10^4
- 2 <= folder[i].length <= 100
- folder[i] 只包含小写字母和 '/'
- folder[i] 总是以字符 '/' 起始
- folder 每个元素都是 唯一 的
思路
有一个文件夹列表,删除其中所有的子文件夹。
将文件夹列表排序,父目录总是会先出现,记为 prev
,使用 startsWith
判断当前目录是否是子目录,如果不是更新 prev
,并加入结果集合,否则直接跳过。需要注意 prev
需要以 /
结尾,否则会错误地匹配,比如 /a/b/c
并不是 /a/b/ca
的父目录。
也可以使用字典树来解决该问题,构造字典树,将最后一个节点标记为文件夹列表的下标,dfs 字典树,如果遇到标记非空则直接返回,不再查找子文件夹。
代码
/**
* @date 2025-07-19 10:57
*/
public class RemoveSubfolders1233 {
public List<String> removeSubfolders(String[] folder) {
Arrays.sort(folder);
String prev = ".";
List<String> res = new ArrayList<>();
for (String path : folder) {
if (path.startsWith(prev)) {
continue;
}
res.add(path);
prev = path + "/";
}
return res;
}
}