Other answers explain what happens: when the output of the template argument finds two ways to output the template argument, it looks at each individually, and they should all agree exactly.
You can probably get this class to work the way you planned, making sure that the second use of t is in an "undetectable context":
template<typename T> struct identity { typedef T type; }; struct blah { template<class t> blah(void(*)(t), typename identity<t>::type){} };
Thus, when the blah constructor is called, C ++ infers t from the function pointer, but does not try to infer it from the second argument. The inferred type is then replaced in both places.
source share