Мы работаем над программой для решения игры Boggle, и вся программа должна быть выполнена менее чем за 0,1 с. Мы вставляем словарь в наш код стандартным вводом (который длится 0,05 секунды, половина нашего максимального времени). Мы используем следующие функции для добавления слов в словарь, которые длятся по 0,1 секунды:
void Node::addWord(const char* word){
const char idx = *word - 'a';
if(!mChildren[idx]) mChildren[idx] = new Node(*word);
if(strlen(word) > 1) mChildren[idx]->addWord(word + 1);
else mChildren[idx]->setMarker(true);
}
void Trie::addDictionary(const vector<string>* aux){
auto length = aux->size();
Node* current = root;
for (size_t i = 0; i < length; i++) {
int len = aux->at(i).length();
if (len >= 3 && len <= DIM*DIM + 1) {
current->addWord(aux->at(i).c_str());
}
}
}
В этом случае DIM = 4 (это размер платы NxN в Boggle), а aux — это вектор, в который сбрасываются все данные со стандартного ввода. Мы навязываем условие len> = 3, потому что нам нужны слова только с 3 буквами и более.
Есть идеи по улучшению скорости этих функций?
Лучший способ повысить скорость этих функций — запустить на них профилировщик. Я бы не стал оптимизировать подобный код, пока вы не запустите профилировщик.
При этом мой прогноз будет состоять в том, что, если вы запустите профилировщик, вы обнаружите, что большая часть времени выполнения (например, 90%) будет new Node(*word)
, Распределение кучи медленное по сравнению с другими операциями, которые вы делаете. Как медленно? Это зависит от вашей платформы, поэтому вы должны зарегистрироваться, чтобы найти горячие точки. То, что занимает много времени на одной платформе, может занимать очень мало времени на других.
Запустите профилировщик и определите правильность моей заявки. Если это правильно, то я рекомендую пулы, выделяющие узлы, чтобы уменьшить количество распределений, которые должны произойти.
Других решений пока нет …