使用 VS2012 的静态地图和 std::function 编译器错误
Compiler Error with static map and std::function using VS2012
我正在尝试使用静态 std::map
,其中 enum
作为键,std::function
作为值。静态地图使用来自 boost 1.52 的 boost::assign::map_list_of
初始化。我正在使用 boost 来执行此操作,因为 VS2012 不知道 c++11 初始化程序列表。我的代码在 wandbox
上运行良好
这是我的代码的样子
#include <iostream>
#include <string>
#include <map>
#include <functional>
#include <utility>
#include <boost/assign/list_of.hpp>
namespace ba = boost::assign;
class Foo
{
public:
enum class MapKeys
{
Key1,
Key2
};
typedef std::map<Foo::MapKeys, std::function<bool(Foo*, int i)>> fooMap;
bool key_based_action(Foo::MapKeys m, int i) {
return((Foo::myMap.at(m))(this, i));
}
private:
static const Foo::fooMap myMap ;
bool key1_handler(int i) {
if (i > 0) {
return true;
}
return false;
}
bool key2_handler(int i) {
if (i < 0) {
return true;
}
return false;
}
};
//const Foo::fooMap Foo::myMap =
//{
// {Foo::MapKeys::Key1, std::mem_fn(&Foo::key1_handler)},
// {Foo::MapKeys::Key2, std::mem_fn(&Foo::key2_handler)}
//};
const Foo::fooMap Foo::myMap =
ba::map_list_of(Foo::MapKeys::Key1, std::mem_fn(&Foo::key1_handler))
(Foo::MapKeys::Key2, std::mem_fn(&Foo::key2_handler));
int main(void)
{
Foo f;
if(f.key_based_action(Foo::MapKeys::Key1, 1))
std::cout << "Key1 returned true" << std::endl;
if(f.key_based_action(Foo::MapKeys::Key2, 1))
std::cout << "Key2 returned true" << std::endl;
return 0;
}
错误信息:
1>c:\program files (x86)\microsoft visual studio 11.0\vc\include\xrefwrap(518): error C2248: "std::_Callable_base<_Ty,_Indirect>::operator =": Kein Zugriff auf private Member, dessen Deklaration in der std::_Callable_base<_Ty,_Indirect>-Klasse erfolgte.
1> with
1> [
1> _Ty=bool (__thiscall Foo::* )(int),
1> _Indirect=false
1> ]
1> c:\program files (x86)\microsoft visual studio 11.0\vc\include\xrefwrap(331): Siehe Deklaration von 'std::_Callable_base<_Ty,_Indirect>::operator ='
1> with
1> [
1> _Ty=bool (__thiscall Foo::* )(int),
1> _Indirect=false
1> ]
1> Diese Diagnose trat in der vom Compiler generierten Funktion "std::_Callable_pmf<_Ty,_Memty> &std::_Callable_pmf<_Ty,_Memty>::operator =(const std::_Callable_pmf<_Ty,_Memty> &)" auf.
1> with
1> [
1> _Ty=bool (__thiscall Foo::* )(int),
1> _Memty=Foo
1> ]
上面写着类似std::_Callable_base<_Ty,_Indirect>
.
中声明的私有成员没有访问权限之类的话
因为这适用于 gcc / clang 和 visual studio 的更高版本(使用 VS2015CE 和 boost 1.63 测试)我想这是 VS2012 中的某种错误/缺失功能。所以我可以通过不使用静态地图来解决这个问题,但是持有地图的对象生命周期很短,而且地图会被一遍又一遍地初始化。任何提示我如何使用静态地图和 VS2012 执行此操作(我必须使用此版本,无法更改此版本)?
对我来说,这个问题的答案是按照 Dan Masek 的建议使用 boost::function
。
这是更新后的代码,我也更新了 wandbox 示例
#include <iostream>
#include <string>
#include <map>
#include <utility>
#include <boost/function.hpp>
#include <boost/assign/list_of.hpp>
namespace ba = boost::assign;
class Foo
{
public:
enum class MapKeys
{
Key1,
Key2
};
typedef std::map<Foo::MapKeys, boost::function<bool(Foo*, int i)>> fooMap;
bool key_based_action(Foo::MapKeys m, int i) {
return((Foo::myMap.at(m))(this, i));
}
private:
static const Foo::fooMap myMap ;
bool key1_handler(int i) {
if (i > 0) {
return true;
}
return false;
}
bool key2_handler(int i) {
if (i < 0) {
return true;
}
return false;
}
};
//const Foo::fooMap Foo::myMap =
//{
// {Foo::MapKeys::Key1, std::mem_fn(&Foo::key1_handler)},
// {Foo::MapKeys::Key2, std::mem_fn(&Foo::key2_handler)}
//};
const Foo::fooMap Foo::myMap =
ba::map_list_of(Foo::MapKeys::Key1, &Foo::key1_handler)
(Foo::MapKeys::Key2, &Foo::key2_handler);
int main(void)
{
Foo f;
if(f.key_based_action(Foo::MapKeys::Key1, 1))
std::cout << "Key1 returned true" << std::endl;
if(f.key_based_action(Foo::MapKeys::Key2, 1))
std::cout << "Key2 returned true" << std::endl;
return 0;
}
我正在尝试使用静态 std::map
,其中 enum
作为键,std::function
作为值。静态地图使用来自 boost 1.52 的 boost::assign::map_list_of
初始化。我正在使用 boost 来执行此操作,因为 VS2012 不知道 c++11 初始化程序列表。我的代码在 wandbox
这是我的代码的样子
#include <iostream>
#include <string>
#include <map>
#include <functional>
#include <utility>
#include <boost/assign/list_of.hpp>
namespace ba = boost::assign;
class Foo
{
public:
enum class MapKeys
{
Key1,
Key2
};
typedef std::map<Foo::MapKeys, std::function<bool(Foo*, int i)>> fooMap;
bool key_based_action(Foo::MapKeys m, int i) {
return((Foo::myMap.at(m))(this, i));
}
private:
static const Foo::fooMap myMap ;
bool key1_handler(int i) {
if (i > 0) {
return true;
}
return false;
}
bool key2_handler(int i) {
if (i < 0) {
return true;
}
return false;
}
};
//const Foo::fooMap Foo::myMap =
//{
// {Foo::MapKeys::Key1, std::mem_fn(&Foo::key1_handler)},
// {Foo::MapKeys::Key2, std::mem_fn(&Foo::key2_handler)}
//};
const Foo::fooMap Foo::myMap =
ba::map_list_of(Foo::MapKeys::Key1, std::mem_fn(&Foo::key1_handler))
(Foo::MapKeys::Key2, std::mem_fn(&Foo::key2_handler));
int main(void)
{
Foo f;
if(f.key_based_action(Foo::MapKeys::Key1, 1))
std::cout << "Key1 returned true" << std::endl;
if(f.key_based_action(Foo::MapKeys::Key2, 1))
std::cout << "Key2 returned true" << std::endl;
return 0;
}
错误信息:
1>c:\program files (x86)\microsoft visual studio 11.0\vc\include\xrefwrap(518): error C2248: "std::_Callable_base<_Ty,_Indirect>::operator =": Kein Zugriff auf private Member, dessen Deklaration in der std::_Callable_base<_Ty,_Indirect>-Klasse erfolgte.
1> with
1> [
1> _Ty=bool (__thiscall Foo::* )(int),
1> _Indirect=false
1> ]
1> c:\program files (x86)\microsoft visual studio 11.0\vc\include\xrefwrap(331): Siehe Deklaration von 'std::_Callable_base<_Ty,_Indirect>::operator ='
1> with
1> [
1> _Ty=bool (__thiscall Foo::* )(int),
1> _Indirect=false
1> ]
1> Diese Diagnose trat in der vom Compiler generierten Funktion "std::_Callable_pmf<_Ty,_Memty> &std::_Callable_pmf<_Ty,_Memty>::operator =(const std::_Callable_pmf<_Ty,_Memty> &)" auf.
1> with
1> [
1> _Ty=bool (__thiscall Foo::* )(int),
1> _Memty=Foo
1> ]
上面写着类似std::_Callable_base<_Ty,_Indirect>
.
因为这适用于 gcc / clang 和 visual studio 的更高版本(使用 VS2015CE 和 boost 1.63 测试)我想这是 VS2012 中的某种错误/缺失功能。所以我可以通过不使用静态地图来解决这个问题,但是持有地图的对象生命周期很短,而且地图会被一遍又一遍地初始化。任何提示我如何使用静态地图和 VS2012 执行此操作(我必须使用此版本,无法更改此版本)?
对我来说,这个问题的答案是按照 Dan Masek 的建议使用 boost::function
。
这是更新后的代码,我也更新了 wandbox 示例
#include <iostream>
#include <string>
#include <map>
#include <utility>
#include <boost/function.hpp>
#include <boost/assign/list_of.hpp>
namespace ba = boost::assign;
class Foo
{
public:
enum class MapKeys
{
Key1,
Key2
};
typedef std::map<Foo::MapKeys, boost::function<bool(Foo*, int i)>> fooMap;
bool key_based_action(Foo::MapKeys m, int i) {
return((Foo::myMap.at(m))(this, i));
}
private:
static const Foo::fooMap myMap ;
bool key1_handler(int i) {
if (i > 0) {
return true;
}
return false;
}
bool key2_handler(int i) {
if (i < 0) {
return true;
}
return false;
}
};
//const Foo::fooMap Foo::myMap =
//{
// {Foo::MapKeys::Key1, std::mem_fn(&Foo::key1_handler)},
// {Foo::MapKeys::Key2, std::mem_fn(&Foo::key2_handler)}
//};
const Foo::fooMap Foo::myMap =
ba::map_list_of(Foo::MapKeys::Key1, &Foo::key1_handler)
(Foo::MapKeys::Key2, &Foo::key2_handler);
int main(void)
{
Foo f;
if(f.key_based_action(Foo::MapKeys::Key1, 1))
std::cout << "Key1 returned true" << std::endl;
if(f.key_based_action(Foo::MapKeys::Key2, 1))
std::cout << "Key2 returned true" << std::endl;
return 0;
}