{-# LANGUAGE OverlappingInstances, MultiParamTypeClasses, FunctionalDependencies, FlexibleContexts, FlexibleInstances, UndecidableInstances #-} import qualified Prelude import Prelude hiding ((+), (*)) import qualified Prelude newtype WInt = WInt { unwrap :: Int } liftW f a b = WInt $ f (unwrap a) (unwrap b) class Times a b c | a b -> c where (*) :: a -> b -> c instance Times WInt WInt WInt where (*) = liftW (Prelude.*) instance (Times a b c) => Times a (r -> b) (r -> c) where x * g = \v -> x * g v instance Times (a -> b) a b where f * y = f y two = WInt 2 six = WInt 6 test :: WInt test = (two*(\x -> two*x))*six main = undefined