#include <iostream>
#include <memory>
#include <vector>
#include <string>
#include <algorithm>
#include <stdexcept>
class FileSystemNode {
public:
virtual ~FileSystemNode() = default;
virtual void show(int depth = 0) const = 0;
virtual int getSize() const = 0;
virtual void add(std::shared_ptr<FileSystemNode> child) {
throw std::logic_error("Cannot add to a leaf node.");
}
virtual void remove(std::shared_ptr<FileSystemNode> child) {
throw std::logic_error("Cannot remove from a leaf node.");
}
};
class File : public FileSystemNode {
std::string name_;
int size_;
public:
File(const std::string& name, int size) : name_(name), size_(size) {}
void show(int depth = 0) const override {
std::cout << std::string(depth, '-')
<< "File: " << name_ << " (" << size_ << "KB)" << std::endl;
}
int getSize() const override {
return size_;
}
};
class Directory : public FileSystemNode {
std::string name_;
std::vector<std::shared_ptr<FileSystemNode>> children_;
public:
Directory(const std::string& name) : name_(name) {}
void add(std::shared_ptr<FileSystemNode> child) override {
children_.push_back(child);
}
void remove(std::shared_ptr<FileSystemNode> child) override {
auto it = std::find(children_.begin(), children_.end(), child);
if (it != children_.end()) {
children_.erase(it);
}
}
void show(int depth = 0) const override {
std::cout << std::string(depth, '-')
<< "Directory: " << name_ << " (total: " << getSize() << "KB)" << std::endl;
for (const auto& child : children_) {
child->show(depth + 2);
}
}
int getSize() const override {
int total = 0;
for (const auto& child : children_) {
total += child->getSize();
}
return total;
}
};
int main() {
auto root = std::make_shared<Directory>("root");
root->add(std::make_shared<File>("file1.txt", 100));
root->add(std::make_shared<File>("file2.txt", 200));
auto subDir = std::make_shared<Directory>("subdir");
subDir->add(std::make_shared<File>("file3.txt", 300));
subDir->add(std::make_shared<File>("file4.txt", 400));
auto nestedDir = std::make_shared<Directory>("nested");
nestedDir->add(std::make_shared<File>("file5.txt", 50));
subDir->add(nestedDir);
root->add(subDir);
std::cout << "File system structure:\n";
root->show();
std::cout << "\nTotal size of root: " << root->getSize() << "KB" << std::endl;
try {
auto file = std::make_shared<File>("orphan.txt", 10);
file->add(std::make_shared<File>("child.txt", 5));
} catch (const std::exception& e) {
std::cout << "Exception caught: " << e.what() << std::endl;
}
return 0;
}