lower_bound在多线程下容易出问题

lower_bound方法一般应用于排序的系列,比如vector、list等,在插入新的记录前通过这个方法找到插入点,当找不到插入点时追加到最后即可,由此可以生成排序的系列。同样使用这个方法可以找到系列中的某一对象,binary_search方法就是使用的这个方法。

今天我在测试一个项目时发现一个奇怪的现象,就是在多线程情况下通过这个方法查找某一对象时,系列中的某一个对象的值会发生变化,而变化的值有可能还会变成其它值,结果将会导致已排序的系列变成无序,后果可想而知。

假设系列中的每个元素是下面的结构:
typedef struct tagMbParam
{
 std::string strParamName;
 unsigned char nType;
 unsigned short nPduAddr;
} MB_PARAM, *PMB_PARAM;

我们给lower_bound指定一个排序函数,按strParamName从小到大排序:
bool MBPSortFun(MB_PARAM first, MB_PARAM second)
{
 if (first.strParamName < second.strParamName)
 {
  return true;
 }
 else
 {
  return false;
 }
}

我们用下面的方法查找某一对象:
 MB_PARAM mb;
 mb.strParamName = "要查找对象对应的值";
 系列类型::iterator it = lower_bound(系列.begin(), 系列.end(), mb, MBPSortFun);

在单线程时没有问题,在多线程情况下,系统中某一个元素中的strParamName会发生变化,导致问题出现。

我怀疑是不是lower_bound不支持多线程或支持得不够好,因此在该函数的调用前后加上临界区,问题不再出现:
 EnterCriticalSection(&s_csParam);
 系列类型::iterator it = lower_bound(系列.begin(), 系列.end(), mb, MBPSortFun);
 LeaveCriticalSection(&s_csParam);

Leave a Reply