Сначала я сериализую все элементы дерева в файл DAT, а затем могу загрузить файл обратно.
Я могу восстановить древовидную структуру в правильной иерархии.
Нокак только элементы восстановлены, и я перебираю их, я получаю неверный индекс, и приложение вылетает.
void iterate(const QModelIndex & index, boost::archive::text_iarchive &ar, TreeModel * model)
{
if (index.isValid())
{
TreeItem* currentTreeItem = model->getItem(index);
Container* containerRestored;
ar & containerRestored;
currentTreeItem->setContainer(containerRestored);
}
else
qDebug() << "Index is not valid";
if (!model->hasChildren(index) || (index.flags() & Qt::ItemNeverHasChildren))
{
return;
}
auto rows = model->rowCount(index);
for (int i = 0; i < rows; ++i)
iterate(model->index(i, 0, index), ar, model);
}
Вот так я восстанавливаю элементы моего дерева из файла DAT.
void TreeModel::loadFileToModel(const QModelIndex &parent)
{
const QString path = "datastream.dat";
QMimeData mimeData;
QFile file(path);
file.open(QIODevice::ReadOnly);
QDataStream out(&file);
out >> mimeData;
if (!mimeData.hasFormat(s_treeNodeMimeType)) {
return;
}
QByteArray data = mimeData.data(s_treeNodeMimeType);
QDataStream stream(&data, QIODevice::ReadOnly);
TreeItem *parentNode = this->getRoot();
int count;
stream >> count;
int row = 0;
TreeItem *node;
for (int i = 0; i < count; ++i) {
// Decode data from the QMimeData
qlonglong nodePtr;
int childCount;
stream >> nodePtr;
stream >> childCount;
Container cont;
TreeItem *nodeNew = new TreeItem( &cont);
beginInsertRows(parent, row, row);
parentNode->insertChild(row, nodeNew);
endInsertRows();
for (int k = 0; k < childCount; k++)
{
restoreTreeFromFile(stream, nodeNew, k);
}
++row;
}
}
/////////////////////////////////////////////////////////////////////////////////
TreeItem * TreeModel::restoreTreeFromFile(QDataStream & ds, TreeItem* parent, int row)
{
Container cont;
// Restore the info from the stream
int childCount;
qlonglong nodePtr;
QModelIndex parentIndex = indexForTreeItem(parent);
ds >> nodePtr;
ds >> childCount;
TreeItem *currentItem = reinterpret_cast<TreeItem *>(nodePtr);
if (currentItem == nullptr)
return nullptr;
TreeItem *thisItem = new TreeItem(&cont, currentItem->parent());
parent->insertChild(row, thisItem);
for (auto nChild = 0; nChild < childCount; ++nChild)
{
restoreTreeFromFile(ds, thisItem, nChild);
}
return thisItem;
}
//////////////////////////////////////////////
void TreeItem::insertChild(int pos, TreeItem *child)
{
childItems.insert(pos, child);
child->parentItem = this;
}