diff options
author | Sylvain Henry <sylvain@haskus.fr> | 2020-08-23 17:42:13 +0200 |
---|---|---|
committer | Marge Bot <ben+marge-bot@smart-cactus.org> | 2021-01-22 15:02:05 -0500 |
commit | 887eb6ec23eed243604f71c025d280c0b854f4c4 (patch) | |
tree | e4be1a7822ca5b44a3a79a940b16b82ee3637fe7 /libraries/base | |
parent | 6fbfde95d3612fdd747b9785d409dc32e3fdd744 (diff) | |
download | haskell-887eb6ec23eed243604f71c025d280c0b854f4c4.tar.gz |
Enhance Data instance generation
Use `mkConstrTag` to explicitly pass the constructor tag instead of
using `mkConstr` which queries the tag at runtime by querying the index
of the constructor name (a string) in the list of constructor names.
Perf improvement:
T16577(normal) ghc/alloc 11325573876.0 9249786992.0 -18.3% GOOD
Thanks to @sgraf812 for suggesting an additional list fusion fix during
reviews.
Metric Decrease:
T16577
Diffstat (limited to 'libraries/base')
-rw-r--r-- | libraries/base/Data/Data.hs | 17 |
1 files changed, 12 insertions, 5 deletions
diff --git a/libraries/base/Data/Data.hs b/libraries/base/Data/Data.hs index 4ede199e39..0d4ef944a1 100644 --- a/libraries/base/Data/Data.hs +++ b/libraries/base/Data/Data.hs @@ -85,6 +85,7 @@ module Data.Data ( Fixity(..), -- ** Constructors mkConstr, + mkConstrTag, mkIntegralConstr, mkRealConstr, mkCharConstr, @@ -120,6 +121,7 @@ import Data.Eq import Data.Maybe import Data.Monoid import Data.Ord +import Data.List (findIndex) import Data.Typeable import Data.Version( Version(..) ) import GHC.Base hiding (Any, IntRep, FloatRep) @@ -628,10 +630,9 @@ mkDataType str cs = DataType , datarep = AlgRep cs } - -- | Constructs a constructor -mkConstr :: DataType -> String -> [String] -> Fixity -> Constr -mkConstr dt str fields fix = +mkConstrTag :: DataType -> String -> Int -> [String] -> Fixity -> Constr +mkConstrTag dt str idx fields fix = Constr { conrep = AlgConstr idx , constring = str @@ -639,9 +640,15 @@ mkConstr dt str fields fix = , confixity = fix , datatype = dt } + +-- | Constructs a constructor +mkConstr :: DataType -> String -> [String] -> Fixity -> Constr +mkConstr dt str fields fix = mkConstrTag dt str idx fields fix where - idx = head [ i | (c,i) <- dataTypeConstrs dt `zip` [1..], - showConstr c == str ] + idx = case findIndex (\c -> showConstr c == str) (dataTypeConstrs dt) of + Just i -> i+1 -- ConTag starts at 1 + Nothing -> errorWithoutStackTrace $ + "Data.Data.mkConstr: couldn't find constructor " ++ str -- | Gets the constructors of an algebraic datatype |