Put the include depenency table into a separate class, and cache it when possible.

This commit is contained in:
Erik Verbruggen
2010-03-17 12:34:29 +01:00
parent 6ed0cd5d32
commit 1cc5e1fe01
7 changed files with 239 additions and 117 deletions

View File

@@ -570,109 +570,3 @@ void Snapshot::simplified_helper(Document::Ptr doc, Snapshot *snapshot) const
}
}
}
QStringList Snapshot::filesDependingOn(const QString &fileName) const
{
const int N = size();
QVector<QString> files(N);
QHash<QString, int> fileIndex;
QHash<int, QList<int> > includes;
QVector<QBitArray> includeMap(N);
dependency_helper(files, fileIndex, includes, includeMap);
int index = fileIndex.value(fileName, -1);
if (index == -1) {
qWarning() << fileName << "not in the snapshot";
return QStringList();
}
QStringList deps;
for (int i = 0; i < files.size(); ++i) {
const QBitArray &bits = includeMap.at(i);
if (bits.testBit(index))
deps.append(files.at(i));
}
return deps;
}
QHash<QString, QStringList> Snapshot::dependencyTable() const
{
const int N = size();
QVector<QString> files(N);
QHash<QString, int> fileIndex;
QHash<int, QList<int> > includes;
QVector<QBitArray> includeMap(N);
dependency_helper(files, fileIndex, includes, includeMap);
QHash<QString, QStringList> depMap;
for (int index = 0; index < files.size(); ++index) {
QStringList deps;
for (int i = 0; i < files.size(); ++i) {
const QBitArray &bits = includeMap.at(i);
if (bits.testBit(index))
deps.append(files.at(i));
}
depMap[files.at(index)] = deps;
}
return depMap;
}
void Snapshot::dependency_helper(QVector<QString> &files,
QHash<QString, int> &fileIndex,
QHash<int, QList<int> > &includes,
QVector<QBitArray> &includeMap) const
{
int i = 0;
for (const_iterator it = begin(); it != end(); ++it, ++i) {
files[i] = it.key();
fileIndex[it.key()] = i;
}
for (int i = 0; i < files.size(); ++i) {
if (Document::Ptr doc = document(files.at(i))) {
QBitArray bitmap(files.size());
QList<int> directIncludes;
foreach (const QString &includedFile, doc->includedFiles()) {
int index = fileIndex.value(includedFile);
if (index == -1)
continue;
else if (! directIncludes.contains(index))
directIncludes.append(index);
bitmap.setBit(index, true);
}
includeMap[i] = bitmap;
includes[i] = directIncludes;
}
}
bool changed;
do {
changed = false;
for (int i = 0; i < files.size(); ++i) {
QBitArray bitmap = includeMap.value(i);
QBitArray previousBitmap = bitmap;
foreach (int includedFileIndex, includes.value(i)) {
bitmap |= includeMap.value(includedFileIndex);
}
if (bitmap != previousBitmap) {
includeMap[i] = bitmap;
changed = true;
}
}
} while (changed);
}