1233-remove-sub-folders-from-the-filesystem¶
Try it on leetcode
Description¶
Given a list of folders folder
, return the folders after removing all sub-folders in those folders. You may return the answer in any order.
If a folder[i]
is located within another folder[j]
, it is called a sub-folder of it. A sub-folder of folder[j]
must start with folder[j]
, followed by a "/"
. For example, "/a/b"
is a sub-folder of "/a"
, but "/b"
is not a sub-folder of "/a/b/c"
.
The format of a path is one or more concatenated strings of the form: '/'
followed by one or more lowercase English letters.
- For example,
"/leetcode"
and"/leetcode/problems"
are valid paths while an empty string and"/"
are not.
Example 1:
Input: folder = ["/a","/a/b","/c/d","/c/d/e","/c/f"] Output: ["/a","/c/d","/c/f"] Explanation: Folders "/a/b" is a subfolder of "/a" and "/c/d/e" is inside of folder "/c/d" in our filesystem.
Example 2:
Input: folder = ["/a","/a/b/c","/a/b/d"] Output: ["/a"] Explanation: Folders "/a/b/c" and "/a/b/d" will be removed because they are subfolders of "/a".
Example 3:
Input: folder = ["/a/b/c","/a/b/ca","/a/b/d"] Output: ["/a/b/c","/a/b/ca","/a/b/d"]
Constraints:
1 <= folder.length <= 4 * 104
2 <= folder[i].length <= 100
folder[i]
contains only lowercase letters and'/'
.folder[i]
always starts with the character'/'
.- Each folder name is unique.
Solution(Python)¶
class TrieNode:
def __init__(self):
self.children = {}
self.isEndOfFolder = False
class Solution:
def __init__(self):
self.root = TrieNode()
def removeSubfolders(self, folder: List[str]) -> List[str]:
return self.trie_(folder)
# Time Complexity: O(N*L^2)
# Space Complexity: O(N*L)
def set_(self, folder: List[str]) -> List[str]:
folderSet = set(folder)
result = []
for folder in folder:
isSubFolder = False
prefix = folder
while not prefix == "":
pos = prefix.rfind("/")
if not pos:
break
prefix = prefix[0:pos]
if prefix in folderSet:
isSubFolder = True
break
if not isSubFolder:
result.append(folder)
return result
# Time Complexity: O(N*L*logN)
# Space Complexity: O(N*L)
def sort_(self, folder: List[str]) -> List[str]:
folder.sort()
result = []
for f in folder:
if len(result) == 0:
result.append(f)
continue
lastfolder = result[-1]
lastfolder+="/"
if not f.startswith(lastfolder):
result.append(f)
return result
# Time Complexity: O(N*L)
# Space Complexity: O(N*L)
def trie_(self, folder: List[str]) -> List[str]:
for path in folder:
cur_node = self.root
folders = path.split("/")
for foldername in folders:
if foldername == "":
continue
if foldername not in cur_node.children:
cur_node.children[foldername] = TrieNode()
cur_node = cur_node.children[foldername]
cur_node.isEndOfFolder = True
result = []
for path in folder:
current_node = self.root
folders = path.split("/")
is_subfolder = False
for i, folder_name in enumerate(folders):
if folder_name == "":
continue
next_node = current_node.children[folder_name]
# Check if the current folder path is a subfolder of an existing folder
if next_node.isEndOfFolder and i != len(folders) - 1:
is_subfolder = True
break # Found a subfolder
current_node = next_node
# If not a subfolder, add to the result
if not is_subfolder:
result.append(path)
return result