C++ 双链接双向n-树的遍历
我有一个数据结构,它映射了基因的多种剪接异构体,这意味着图中的每个元素都可以是任何其他元素(不包括自身)的前身或继任者。 结构可能是A-B-C-D、A-C-E等等 为了表示这一点,我将数据文件读入一个元素C++ 双链接双向n-树的遍历,c++,algorithm,data-structures,C++,Algorithm,Data Structures,我有一个数据结构,它映射了基因的多种剪接异构体,这意味着图中的每个元素都可以是任何其他元素(不包括自身)的前身或继任者。 结构可能是A-B-C-D、A-C-E等等 为了表示这一点,我将数据文件读入一个元素 class El { vector<El*> left, right; T content; }; El类{ 向量左,右; T含量; }; 因此每个元素E包含的都是前置和后继元素,而前置和后继元素也链接回E。这是构造结构所必需的。出于搜索原因,有必要从结构的任何节点开始
class El {
vector<El*> left, right;
T content;
};
El类{
向量左,右;
T含量;
};
因此每个元素E包含的都是前置和后继元素,而前置和后继元素也链接回E。这是构造结构所必需的。出于搜索原因,有必要从结构的任何节点开始遍历,但当使用简单的宽度优先或宽度优先方法遍历时,这将导致无限圆(此处:从C开始;遍历左:(B,A),(A);从A开始遍历右:(C,E),(B,C,…),从C开始遍历左:(B,A),…)
错误代码(无限圆):
矢量起始点;
空心导线(El*El=nullptr){
如果(el==nullptr){
用于(自动节点:起始点(&N){
导线(节点);
}
}
否则{
用于(自动和远程:el->left){
导线测量(ltEl);
}
标准::cout(右){
导线测量(rtEl);
}
}
}
有人能推荐一个合适的方法吗?你可以给El类添加一个标志。flag=0表示您尚未处理该节点,而1表示该节点已被处理并因此停止。根据闵富的想法,我当前的方法是:
class El {
vector<El*> left, right;
uint runID; // init to 0
T content;
};
vector<El*> startpoints;
void traverse(El* el = nullptr) {
static uint runID = 1;
if (el == nullptr) {
for (auto& node : startingpoints) {
traverse(node);
runID++;
}
}
else {
el->runID = runID;
// predecessors
for (auto& ltEl : el->left) {
if (ltEL->runID != runID) {
traverse(ltEl);
}
}
// current
std::cout << *El;
// successors
for (auto& rtEl : el->right) {
if (rtEL->runID != runID) {
traverse(rtEl);
}
}
}
}
El类{
向量左,右;
uint runID;//初始化为0
T含量;
};
向量起始点;
空心导线(El*El=nullptr){
静态uint runID=1;
如果(el==nullptr){
用于(自动节点:起始点(&N){
导线(节点);
runID++;
}
}
否则{
el->runID=runID;
//前辈
用于(自动和远程:el->left){
如果(ltEL->runID!=runID){
导线测量(ltEl);
}
}
//当前
标准::cout(右){
如果(rtEL->runID!=runID){
导线测量(rtEl);
}
}
}
}
啊,谢谢。。。那是个好主意。由于我必须多次访问该方法,因此我对其进行了如下修改,它的效果非常好!
class El {
vector<El*> left, right;
uint runID; // init to 0
T content;
};
vector<El*> startpoints;
void traverse(El* el = nullptr) {
static uint runID = 1;
if (el == nullptr) {
for (auto& node : startingpoints) {
traverse(node);
runID++;
}
}
else {
el->runID = runID;
// predecessors
for (auto& ltEl : el->left) {
if (ltEL->runID != runID) {
traverse(ltEl);
}
}
// current
std::cout << *El;
// successors
for (auto& rtEl : el->right) {
if (rtEL->runID != runID) {
traverse(rtEl);
}
}
}
}