namespace detail { template struct Quux {}; } // namespace detail using FuncPtr = detail::Quux (*(*)(int))(float); struct Foo { template void foo(T arg) const noexcept(true) {} template void operator<<(int) {} template FuncPtr returns_func_ptr(detail::Quux &&) const noexcept(false) { return nullptr; } }; namespace ns { template int foo(char const *str) noexcept(false) { return 0; } template int foo(T t) { return 1; } template FuncPtr returns_func_ptr(detail::Quux &&) { return nullptr; } } // namespace ns int bar() { return 1; } namespace { int anon_bar() { return 1; } auto anon_lambda = [] {}; } // namespace __attribute__((always_inline)) int inlined_foo(const char *str) { if (bool b = bar()) return 1; return 2; } int main() { ns::foo(bar); ns::foo("bar"); ns::foo(anon_lambda); ns::foo(anon_bar); ns::foo)>("method"); ns::returns_func_ptr(detail::Quux{}); Foo f; f.foo(anon_bar); f.operator<< <(2 > 1)>(0); f.returns_func_ptr(detail::Quux{}); inlined_foo("bar"); return 0; }