Remove Sub-Directories from a File System
Last Updated :
21 Nov, 2022
Given an array of strings arr[] consisting of N unique directories in the form of strings, the task is to remove all the subdirectories and print the final array.
A directory S is a subdirectory if there exists any directory D such that S is the prefix of D.
Examples:
Input: arr[] = {“/a”, “/a/j”, “/c/d/e”, “/c/d”, “/b”}
Output: { “/a”, “/c/d”, “/b”}
Explanation: Directory “/a/j” is a subdirectory of directory “/a”, and “/c/d/e” is a subdirectory of directory “/c/d”.
Therefore, remove both of them.
Input: arr[] = {“/a”, “/a/b”, “/a/b/c”, “/a/b/c/d”}
Output: {“/a”}
Explanation: All directories are subdirectories of “/a”
Naive Approach: The simplest approach is to traverse the array to check for each string, if there exists a string having it as the prefix and remove such strings from the array.
Time Complexity: O(len * N2), where len is the length of the longest string in the array.
Auxiliary Space: O(N)
Efficient Approach: The idea is to sort the given array and compare the current directory at position i with the previous directory at index (i -1). If arr[i – 1] is the prefix of arr[i] then remove arr[i]. After checking the whole array, print the remaining directories. Follow the below steps to solve the problem:
- Sort all the directories alphabetically and initialize a vector res.
- Insert the first directory into res.
- Check each directory with the last valid directory i.e., last directory from res.
- The directory is invalid(sub-directory) if it equals to some prefix of the previous valid directory. Else it is valid.
- If the current directory is valid, then add it to res.
- Print all the directories present in res after done traversing.
Below is the implementation of the above approach:
C++
#include <bits/stdc++.h>
using namespace std;
void eraseSubdirectory(vector<string>& dir)
{
vector<string> res;
sort(dir.begin(), dir.end());
res.push_back(dir[0]);
cout << "{" << dir[0] << ", " ;
for ( int i = 1; i < dir.size(); i++) {
string curr = dir[i];
string prev = res.back();
int l = prev.length();
if (curr.length() > l && curr[l] == '/'
&& prev == curr.substr(0, l))
continue ;
res.push_back(curr);
cout << curr << ", " ;
}
cout << "}\n" ;
}
int main()
{
vector<string> dir
= { "/a" , "/a/j" , "/c/d/e" ,
"/c/d" , "/b" };
eraseSubdirectory(dir);
return 0;
}
|
Java
import java.io.*;
import java.util.*;
class GFG{
static void eraseSubdirectory(ArrayList<String> dir)
{
ArrayList<String> res = new ArrayList<String>();
Collections.sort(dir);
res.add(dir.get( 0 ));
System.out.print( "{" + dir.get( 0 ) + ", " );
for ( int i = 1 ; i < dir.size(); i++)
{
String curr = dir.get(i);
String prev = res.get(res.size() - 1 );
int l = prev.length();
if (curr.length() > l &&
curr.charAt(l) == '/' &&
prev.equals(curr.substring( 0 , l)))
continue ;
res.add(curr);
System.out.print(curr + ", " );
}
System.out.print( "}\n" );
}
public static void main(String[] args)
{
ArrayList<String> dir = new ArrayList<String>(Arrays.asList(
"/a" , "/a/j" , "/c/d/e" , "/c/d" , "/b" ));
eraseSubdirectory(dir);
}
}
|
Python3
def eraseSubdirectory( dir ):
res = []
dir .sort()
res.append( dir [ 0 ])
print ( "{" , dir [ 0 ], end = ", " )
for i in range ( 1 , len ( dir )):
curr = dir [i]
prev = res[ len (res) - 1 ]
l = len (prev)
if ( len (curr) > l and
curr[l] = = '/' and
prev = = curr[:l]):
continue
res.append(curr)
print (curr, end = ", " )
print ( "}" )
if __name__ = = '__main__' :
dir = [ "/a" , "/a/j" , "/c/d/e" , "/c/d" , "/b" ]
eraseSubdirectory( dir )
|
C#
using System;
using System.Collections;
class GFG{
static void eraseSubdirectory(ArrayList dir)
{
ArrayList res = new ArrayList();
dir.Sort();
res.Add(dir[0]);
Console.Write( "{" + dir[0] + ", " );
for ( int i = 1; i < dir.Count; i++)
{
string curr = ( string )dir[i];
string prev = ( string )res[(res.Count - 1)];
int l = prev.Length;
if (curr.Length > l && curr[l] == '/' &&
prev.Equals(curr.Substring(0, l)))
continue ;
res.Add(curr);
Console.Write(curr + ", " );
}
Console.Write( "}\n" );
}
public static void Main()
{
ArrayList dir = new ArrayList(){ "/a" , "/a/j" ,
"/c/d/e" ,
"/c/d" , "/b" };
eraseSubdirectory(dir);
}
}
|
Javascript
function eraseSubdirectory(dir) {
let res = new Array();
dir.sort();
res.push(dir[0]);
console.log( "{" + dir[0] + ", " );
for (let i = 1; i < dir.length; i++) {
let curr = dir[i];
let prev = res[res.length - 1];
let l = prev.length;
if (curr.length > l &&
curr[l] == '/' && (prev == (curr.substring(0, l))))
continue ;
res.push(curr);
console.log(curr + ", " );
}
console.log( "}\n" );
}
let dir = [ "/a" , "/a/j" , "/c/d/e" , "/c/d" , "/b" ];
eraseSubdirectory(dir);
|
Time Complexity: O(N*log N)
Auxiliary Space: O(N)
Share your thoughts in the comments
Please Login to comment...