
Bin Jin wrote:
Here is a function that will be called everytime by `(*)` in `Num` typeclass
montgKeys :: (PostiveN p, Integral a, Bits a) => p -> a
as you can imagine, I always pass (undefined :: p) as parameter to `montgKeys`, so if it's handled well, it should be memorized for future usage. But tracing shows that both `p2num` and `montgKeys` are evaluated every time being called.
First of all, let us get rid of the argument p. Let's define
newtype W p a = W{unW:: a}
then we can easily re-write montgKeys to give it the following signature:
montgKeys :: (PostiveN p, Integral a, Bits a) => W p a
You can use ScopedTypevariables to set the needed 'p' from the context. So, montgKeys becomes a polymorphic constant, quite like minBound. Now, the hope is that when the types p and a are determined, GHC could specialize montgKeys and turn it into a real constant. Perhaps some RULE or specialize pragmas may help...