std :: function copy operator(MSVC2012)的奇怪行为

时间:2015-04-16 08:10:10

标签: c++ visual-c++ std-function visual-studio-2012

尝试使用函数<>时,我遇到了bad_function_call异常的问题对象

发现问题让我想到下一个简单的样本: http://ideone.com/Mwvw7s

主要摘录:

std::function<void(void*)> f1;
std::function<void(const void*)> f2;
f1 = f2; // Could fail, but didn't

if(f1)
    f1(nullptr); // Should never run
else 
    std::cout << "Skip f1" << std::endl; // Should run

if(f2)
    f2(nullptr);
else 
    std::cout << "Skip f2" << std::endl;

无论f2如何,f1都有效。 此问题仅在MSVC2012上发生(没有尝试任何其他版本的MS编译器)并在GCC中按预期工作。

问题是:

  1. 这个问题MSVC2012是否具体? (任何人都可以在MSVC2013上进行测试)
  2. 这个问题众所周知吗?
  3. [如果1和2是&#39; no&#39;]我应该抱怨谁?
  4. 更新

    1. MSVC2013无法重现此类问题。
    2. 以防万一有人关心,GitHub存储库有问题:https://github.com/comargo/functional_test

1 个答案:

答案 0 :(得分:0)

这似乎是MSVC2012的一个问题; MSVC2013正确运行它(live example)。

从模板的不同实例化(即使用不同的签名)分配function类模板实例化实例委托给构造函数,并由 [func.wrap]的特殊子句处理。 func.con]

  

8 - 后置条件: !*this如果符合以下任何条件:[...]

     
      
  • Ffunction类模板的实例,!f
  •   

我猜想库实现者未能为MSVC2012实现这个子句;在function类模板实例化之间进行转换时,最直接的策略是将源类型包装在转换包装器中;很容易忘记检查源实例是否正在使用。

作为一种解决方法,你可以写:

f2 ? (f1 = f2) : (f1 = nullptr);