In haskell IO type has instance of Monoid:
instance Monoid a => Monoid (IO a) where
mempty = pure empty
if I have three actions which share some state, and change behavior of each other via side effect, this can lead to breaking associativity law, from IO type point of view:
a1:: IO String
a2:: IO String
a3:: IO String
(a1 mappend
a2) mappend
a3 /= a1 mappend
(a2 mappend
a3)
for example if a1,a2,a3 request current time in string, or IO contains some DB which counts for request number. This mean that it can be:
(a1 `mappend` a2) `mappend` a3 == "1"++"2"++"3"
a1 `mappend` (a2 `mappend` a3) == "3"++"1"++"2"
EDIT:
I think I shouldn't have given an example with a db, it confused, more preferred example:
a1 = show <$> getUnixTime
a2 = show <$> getUnixTime
a3 = show <$> getUnixTime
l = (a1 `mappend` a2) `mappend` a3
r = a1 `mappend` (a2 `mappend` a3)
liftA2 (==) l r
**False**
So why IO type is monoid if it can break associativity law? or I missing something?