A new approach to generic functional programming

This paper describes a new approach to generic functional programming, which allows us to define functions generically for all datatypes expressible in Haskell. A generic function is one that is defined by induction on the structure of types. Typical examples include pretty printers, parsers, and comparison functions. The advanced type system of Haskell presents a real challenge: datatypes may be parameterized not only by types but also by type constructors, type definitions may involve mutual recursion, and recursive calls of type constructors can be arbitrarily nested. We show that—despite this complexity—a generic function is uniquely defined by giving cases for primitive types and type constructors (such as disjoint unions and cartesian products). Given this information a generic function can be specialized to arbitrary Haskell datatypes. The key idea of the approach is to model types by terms of the simply typed λ-calculus augmented by a family of recursion operators. While conceptually simple, our approach places high demands on the type system: it requires polymorphic recursion, rank-n types, and a strong form of type constructor polymorphism. Finally, we point out connections to Haskell's class system and show that our approach generalizes type classes in some respects.

[1]  F. Ruehr Structural Polymorphism , 1998 .

[2]  Johan Jeuring,et al.  Polytypic Programming , 1996, Advanced Functional Programming.

[3]  Bruno Courcelle,et al.  Fundamental Properties of Infinite Trees , 1983, Theoretical Computer Science.

[4]  Zhe Yang,et al.  Encoding types in ML-like languages , 1998, ICFP '98.

[5]  Simon L. Peyton Jones,et al.  Type Classes in Haskell , 1994, ESOP.

[6]  Lambert G. L. T. Meertens Calculate Polytypically! , 1996, PLILP.

[7]  Chris Okasaki,et al.  Purely functional data structures , 1998 .

[8]  Alan Mycroft,et al.  Polymorphic Type Schemes and Recursive Definitions , 1984, Symposium on Programming.

[9]  Nancy McCracken,et al.  The Typechecking of Programs with Implicit Type Structure , 1984, Semantics of Data Types.

[10]  Ralf Hinze Polytypic Programming With Ease , 2001, J. Funct. Log. Program..

[11]  Johan Jeuring,et al.  PolyP—a polytypic programming language extension , 1997, POPL '97.

[12]  Philip Wadler,et al.  Theorems for free! , 1989, FPCA.

[13]  Ralf Hinze,et al.  Haskell 98 — A Non−strict‚ Purely Functional Language , 1999 .

[14]  Ralf Hinze,et al.  Manufacturing datatypes , 2001, J. Funct. Program..

[15]  Martín Abadi,et al.  Dynamic typing in polymorphic languages , 1995, Journal of Functional Programming.

[16]  Richard S. Bird,et al.  de Bruijn notation as a nested datatype , 1999, Journal of Functional Programming.

[17]  Ralf Hinze,et al.  A Generic Programming Extension for Haskell , 1999 .

[18]  Tim Sheard,et al.  Type parametric programming , 1993 .

[19]  Mark P. Jones,et al.  A system of constructor classes: overloading and implicit higher-order polymorphism , 1993, FPCA '93.

[20]  R. Bird Introduction to functional programming using Haskell, Second Edition , 1998 .

[21]  Mark P. Jones,et al.  Functional Programming with Overloading and Higher-Order Polymorphism , 1995, Advanced Functional Programming.

[22]  Tim Sheard,et al.  Automatic generation and use of abstract structure operators , 1991, TOPL.

[23]  Ralf Hinze Polytypic Programming With Ease (Extended Abstract) , 1999 .

[24]  Robert Harper,et al.  Compiling polymorphism using intensional type analysis , 1995, POPL '95.

[25]  Ralf Hinze,et al.  Polytypic Functions Over Nested Datatypes , 1999, Discret. Math. Theor. Comput. Sci..

[26]  Johan Jeuring,et al.  PolyLib a library of polytypic functions , 1998 .

[27]  Chris Okasaki,et al.  From fast exponentiation to square matrices: an adventure in types , 1999, ICFP '99.

[28]  Johan Jeuring,et al.  Polytypic Compact Printing and Parsing , 1999, ESOP.

[29]  Simon Peyton-Jones,et al.  Henk: A Typed Intermediate Language , 1997 .

[30]  Graham Hutton,et al.  Bananas in space: extending fold and unfold to exponential types , 1995, FPCA '95.

[31]  J. Y. Girard,et al.  Interpretation fonctionelle et elimination des coupures dans l'aritmetique d'ordre superieur , 1972 .

[32]  Lennart Augustsson,et al.  Cayenne—a language with dependent types , 1998, ICFP '98.

[33]  MorrisettGreg,et al.  Intensional polymorphism in type-erasure semantics , 1998, ICFP '98.

[34]  Ralf Hinze,et al.  Generalizing generalized tries , 2000, Journal of Functional Programming.

[35]  Eugenio Moggi,et al.  Functorial ML , 1998 .

[36]  R. Hinze Numerical Representations as Higher−Order Nested Datatypes , 1998 .

[37]  Karl Fritz Ruehr,et al.  Analytical and structural polymorphism expressed using patterns over types , 1992 .

[38]  Simon Peyton Jones,et al.  Henk: a typed intermediate language , 1997 .

[39]  YangZhe Encoding types in ML-like languages , 1998 .

[40]  Henk Barendregt,et al.  The Lambda Calculus: Its Syntax and Semantics , 1985 .

[41]  Simon L. Peyton Jones,et al.  Compiling Haskell by Program Transformation: A Report from the Trenches , 1996, ESOP.

[42]  Richard S. Bird,et al.  Introduction to functional programming , 1988, Prentice Hall International series in computer science.

[43]  Karl Crary,et al.  Intensional polymorphism in type-erasure semantics , 2002, J. Funct. Program..

[44]  Richard S. Bird,et al.  Nested Datatypes , 1998, MPC.

[45]  Peter J. Freyd Structural Polymorphism , 1993, Theor. Comput. Sci..

[46]  J. Robin B. Cockett,et al.  Shapely Types and Shape Polymorphism , 1994, ESOP.

[47]  Richard S. Bird,et al.  Generalised folds for nested datatypes , 1999, Formal Aspects of Computing.