node to path
This commit is contained in:
parent
1e926dc3e4
commit
83abdea417
6 changed files with 76 additions and 35 deletions
|
|
@ -9,6 +9,33 @@
|
|||
extern std::string gError;
|
||||
typedef std::string Key;
|
||||
|
||||
struct DirectoryKey {
|
||||
DirectoryKey() = default;
|
||||
explicit DirectoryKey(Key val) : val(std::move(val)) {}
|
||||
|
||||
[[nodiscard]] inline bool descentRight(const DirectoryKey& in) const { return in.val > val; }
|
||||
[[nodiscard]] inline bool descentLeft(const DirectoryKey& in) const { return in.val < val; }
|
||||
[[nodiscard]] inline bool exactNode(const DirectoryKey& in) const { return in.val == val; }
|
||||
|
||||
[[nodiscard]] inline const DirectoryKey& getFindKey() const { return *this; }
|
||||
static inline const DirectoryKey& keyInRightSubtree(const DirectoryKey& in) { return in; }
|
||||
static inline const DirectoryKey& keyInLeftSubtree(const DirectoryKey& in) { return in; }
|
||||
|
||||
template <typename NodeType>
|
||||
inline void updateTreeCacheCallBack(NodeType& treeNode) {
|
||||
treeNode.data->mTreeNode = &treeNode;
|
||||
// TODO : update incoming links
|
||||
}
|
||||
|
||||
public:
|
||||
Key val;
|
||||
|
||||
ui32 incomingLinksHard = 0;
|
||||
ui32 incomingLinksDynamic = 0;
|
||||
};
|
||||
|
||||
typedef AvlTree<DirectoryKey, class Node*> DirectoryTree;
|
||||
|
||||
class Node {
|
||||
public:
|
||||
enum Type : ui32 { NONE, DIRECTORY, FILE, LINK } ;
|
||||
|
|
@ -18,6 +45,8 @@ public:
|
|||
|
||||
public:
|
||||
Type mType = NONE;
|
||||
Node* mParent = nullptr;
|
||||
DirectoryTree::Node* mTreeNode = nullptr;
|
||||
};
|
||||
|
||||
class File : public Node {
|
||||
|
|
@ -35,33 +64,7 @@ private:
|
|||
bool mIsHard = false;
|
||||
};
|
||||
|
||||
struct DirectoryKey {
|
||||
DirectoryKey() = default;
|
||||
explicit DirectoryKey(Key val) : val(std::move(val)) {}
|
||||
|
||||
[[nodiscard]] inline bool descentRight(const DirectoryKey& in) const { return in.val > val; }
|
||||
[[nodiscard]] inline bool descentLeft(const DirectoryKey& in) const { return in.val < val; }
|
||||
[[nodiscard]] inline bool exactNode(const DirectoryKey& in) const { return in.val == val; }
|
||||
|
||||
[[nodiscard]] inline const DirectoryKey& getFindKey() const { return *this; }
|
||||
static inline const DirectoryKey& keyInRightSubtree(const DirectoryKey& in) { return in; }
|
||||
static inline const DirectoryKey& keyInLeftSubtree(const DirectoryKey& in) { return in; }
|
||||
|
||||
template <typename NodeType>
|
||||
inline void updateTreeCacheCallBack(const NodeType&) {
|
||||
// TODO : update incoming links
|
||||
}
|
||||
|
||||
public:
|
||||
Key val;
|
||||
|
||||
ui32 incomingLinksHard = 0;
|
||||
ui32 incomingLinksDynamic = 0;
|
||||
};
|
||||
|
||||
class Directory : public Node {
|
||||
typedef AvlTree<DirectoryKey, class Node*> DirectoryTree;
|
||||
|
||||
public:
|
||||
Directory();
|
||||
~Directory() override;
|
||||
|
|
@ -79,6 +82,7 @@ public:
|
|||
mMembers.traverseInorder(mMembers.getRoot(), functor);
|
||||
}
|
||||
|
||||
void getNodePath(Node* node, std::vector<const Key*>& path) const;
|
||||
private:
|
||||
void updateTreeLinkCount(Node* node);
|
||||
void getMaxDepthUtil(ui32 depth, ui32& maxDepth) const;
|
||||
|
|
|
|||
|
|
@ -5,6 +5,20 @@
|
|||
|
||||
#include <sstream>
|
||||
|
||||
// Functionality:
|
||||
// - add node to path conversion
|
||||
// - check for current node deletion
|
||||
// - print current node
|
||||
// - print links and link counts
|
||||
// - update link counts
|
||||
// - add link creation commands
|
||||
|
||||
// Refactor
|
||||
// - Move DirectoryKey inside Node (no need to store pointers from Node to DirectoryTree::Node)
|
||||
// - Merge DirectoryTree::Node and Node (no pointer overhead, requires tree nodes to be consistent, check insertNodeInstead)
|
||||
// - introduce smart pointers
|
||||
// - reconsider switch statements
|
||||
|
||||
class FileSystem {
|
||||
public:
|
||||
FileSystem();
|
||||
|
|
|
|||
|
|
@ -211,12 +211,16 @@ private:
|
|||
}
|
||||
|
||||
inline Node* newNode(KeyArg key, DataArg data) {
|
||||
return new Node(key, data);
|
||||
auto out = new Node(key, data);
|
||||
out->updateTreeCacheCallBack();
|
||||
return out;
|
||||
}
|
||||
|
||||
inline void injectNodeInstead(Node* target, Node* from) {
|
||||
target->data = from->data;
|
||||
std::swap(target->data, from->data);
|
||||
target->key = from->key;
|
||||
target->updateTreeCacheCallBack();
|
||||
from->updateTreeCacheCallBack();
|
||||
}
|
||||
|
||||
inline i64 getNodeHeight(const Node* node) const { return node ? node->mHeight : -1; }
|
||||
|
|
|
|||
|
|
@ -47,6 +47,7 @@ bool Directory::attachNode(const std::vector<Key>& directoryPath, const Key& new
|
|||
|
||||
directory->mMembers.insert(DirectoryKey(newKey), newNode);
|
||||
|
||||
newNode->mParent = directory;
|
||||
updateTreeLinkCount(directory);
|
||||
return true;
|
||||
}
|
||||
|
|
@ -67,6 +68,7 @@ bool Directory::detachNode(const std::vector<Key>& directoryPath, const Key& key
|
|||
}
|
||||
|
||||
directory->mMembers.remove(DirectoryKey(key));
|
||||
removeNode->mParent = nullptr;
|
||||
|
||||
updateTreeLinkCount(directory);
|
||||
return true;
|
||||
|
|
@ -129,9 +131,7 @@ ui32 Directory::getMaxDepth() const {
|
|||
void Directory::dump(std::stringstream& ss) {
|
||||
std::vector<bool> indents;
|
||||
indents.resize(getMaxDepth());
|
||||
|
||||
dumpUtil(ss, 0, indents);
|
||||
|
||||
ss << "\n";
|
||||
}
|
||||
|
||||
|
|
@ -164,4 +164,10 @@ void Directory::dumpUtil(std::stringstream& ss, ui32 currentDepth, std::vector<b
|
|||
return;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
void Directory::getNodePath(Node* node, std::vector<const Key*>& path) const {
|
||||
if (!node || !node->mTreeNode) return;
|
||||
path.push_back(&node->mTreeNode->key.val);
|
||||
getNodePath(node->mParent, path);
|
||||
}
|
||||
|
|
@ -76,7 +76,17 @@ bool FileSystem::changeCurrent(const Path& path) {
|
|||
|
||||
void FileSystem::log() const {
|
||||
std::stringstream ss;
|
||||
ss << " *\n";
|
||||
|
||||
std::vector<const Key*> currentPath;
|
||||
root->getNodePath(currentDirectory, currentPath);
|
||||
std::reverse(currentPath.begin(), currentPath.end());
|
||||
|
||||
ss << "cd - /";
|
||||
for (auto key : currentPath) {
|
||||
ss << *key << "/";
|
||||
}
|
||||
|
||||
ss << "\n";
|
||||
root->dump(ss);
|
||||
std::cout << ss.str();
|
||||
}
|
||||
|
|
|
|||
|
|
@ -12,10 +12,13 @@ int main() {
|
|||
interpreter.interpret("MD /A123");
|
||||
interpreter.interpret("cd /A123");
|
||||
interpreter.interpret("md asd");
|
||||
interpreter.interpret("md asd/asd");
|
||||
interpreter.interpret("md asd/asd/asd");
|
||||
interpreter.interpret("md asd/asd/asd/asd");
|
||||
interpreter.interpret("rd asd");
|
||||
interpreter.interpret("md asd/b");
|
||||
interpreter.interpret("md asd/b/c");
|
||||
interpreter.interpret("md asd/b/c/d");
|
||||
|
||||
interpreter.interpret("cd asd/b/c/d");
|
||||
|
||||
interpreter.interpret("rd d");
|
||||
|
||||
return UnitTest::RunAllTests();
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue