C에서는 데이터 구조에 서로 다른 서명이 있는 함수를 저장해야 하는 시나리오가 발생할 수 있습니다. 문자열 키와 일반 메서드를 해당 값으로 받아들이는 맵 컨테이너가 있다고 가정합니다. 이를 가능하게 하려면 다음 접근 방식을 고려하십시오.
C는 유형 삭제를 위한 std::any 유형을 제공합니다. std::any를 사용하면 정확한 유형을 지정하지 않고도 함수 포인터나 람다 식을 컨테이너에 저장할 수 있습니다. 그러나 저장된 함수를 호출하려면 이를 올바른 유형으로 명시적으로 캐스팅해야 합니다.
명시적인 캐스팅을 극복하려면 템플릿 연산자 연산자( ) 저장된 std::any 객체를 매개변수로 사용하는 사용자 정의 래퍼 클래스에 대해 설명합니다. 이 연산자를 사용하면 명시적인 캐스팅 없이 저장된 함수를 호출할 수 있습니다.
다음은 이러한 래퍼 클래스의 구현 예입니다.
template<typename Ret> struct AnyCallable { AnyCallable() {} template<typename F> AnyCallable(F&& fun) : AnyCallable(std::function(std::forward<F>(fun))) {} template<typename ... Args> AnyCallable(std::function<Ret(Args...)> fun) : m_any(fun) {} template<typename ... Args> Ret operator()(Args&& ... args) { return std::invoke(std::any_cast<std::function<Ret(Args...)>>(m_any), std::forward<Args>(args)...); } std::any m_any; };
In 이 구현에서 AnyCallable 클래스는 저장된 std::any 객체를 래핑하고 지정된 인수로 함수를 호출하는 연산자()를 제공합니다.
AnyCallable 클래스를 사용하면 다음을 수행할 수 있습니다. 다양한 시그니처를 사용하여 함수를 저장하는 맵을 생성하고 이를 동적으로 호출합니다.
void foo(int x, int y) { /* ... */ } void bar(std::string x, int y, int z) { /* ... */ } std::map<std::string, AnyCallable<void>> map; map["foo"] = &foo; map["bar"] = &bar; map["foo"](1, 2); map["bar"]("Hello", 1, 2);
유형 삭제 방식으로 저장된 함수를 호출하는 경우 올바른 시그니처를 전달해야 합니다. 인수 유형을 명시적으로 지정합니다. 유형이 일치하지 않으면 std::bad_any_cast 예외가 발생합니다.
위 내용은 C의 맵에 다른 시그니처를 가진 함수를 어떻게 저장할 수 있습니까?의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!