other version almost works thanks to function object black magic