У меня проблемы с объединением результатов обработки, полученных из нескольких потоков. И я не уверен, правильно ли я использую openmp. В приведенном ниже фрагменте кода показана часть моего кода openmp.
Параметры:
Тема приватная:
it: итератор карты (временная метка, userkey)
ite: итератор карты ((отметка времени, userkey) / int amount)
thread_result_map: typedef map
когда, кто: соответствующее регулярное выражение (временная метка, ключ пользователя)
делится между потоками:
log: массив символов
размер: log.size ()
идентификатор, метка времени, ключ пользователя: boost :: regex pattern
комбинированный_результат_карты: карта определения типа
#pragma omp parallel shared(log, size, identifier, timestamp, userkey) private(it, ite, str_time, str_key, vec_str_result, i, id, str_current, when, who, thread_result_map)
{
#pragma omp for
for (i = 0 ; i < size ; i++){
str_current.push_back(log[i]);
if (log[i] == '\n') {
if (boost::regex_search(str_current, identifier)){
boost::regex_search(str_current, when, timestamp);
str_time = when[0];
boost::regex_search(str_current, who, userkey);
str_key = who[0];
thread_result_map.insert(make_pair(str_time, str_key));
}
str_current = ""; //reset temp string
}
}
#pragma omp critical
{
for (it=thread_result_map.begin(); it!=thread_result_map.end(); it++) {
id = omp_get_thread_num();
cout << thread_result_map[it->first] <<
thread_result_map[it->second];
cout << "tID_" << id << " reducing" << endl;
}
}
}
Как вы можете видеть, каждый поток имеет свой собственный раздел массива char, он анализирует строку за строкой из массива, и если текущая строка идентифицируется по «идентификатору», отметка времени и ключ пользователя добавляются в частную карту результатов потока (строка / строка).
Теперь после цикла у меня есть несколько частных карт результатов потока. Combined_result_map - это карта внутри карты. Ключ - это комбинация ключ / значение результата потоков, а значение - это количество вхождений этой комбинации.
Я анализирую только часть метки времени, поэтому, когда через 1 час один и тот же пользовательский ключ появляется несколько раз, счетчик посещений будет увеличен.
Результат должен выглядеть примерно так:
TIME(MMM/DD/HH/);USERKEY;HITS
May/25/13;SOMEKEY124345;3
Таким образом, у меня нет проблем с комбинированием количества попаданий в критическом разделе (который я удалил) путем указания комбинированных + = результатов.
Но как я могу комбинировать свои карты результатов одинаково? Я знаю, что должен перебирать карты потоков, но когда я помещаю «cout» в цикл для тестирования, каждый поток вызывает его только один раз.
Тестовый запуск моего локального системного журнала дает мне следующий вывод, когда я устанавливаю для всех регулярных выражений значение «error» (чтобы убедиться, что каждая идентифицированная строка будет иметь userkey и временную метку с тем же именем):
Шаблон для разбора строки доступа:
error Pattern for parsing Timestamp:
error Pattern for parsing Userkey:
error
*** Parsing File /var/log/syslog
errortID_0 reducing errortID_1
reducing errortID_2 reducing
errortID_3 reducing
*** Ok! ________________ hits :
418 worktime: 0.0253871s
(Рассчитанные хиты получены из частных счетчиков потоков, которые я удалил в приведенном выше коде)
Таким образом, каждый из моих 4-х потоков выполняет один бросок и выходит из цикла, хотя все вместе должно иметь 418 попаданий. Так что я делаю не так? Как мне перебрать результаты из моей открытой области?