type inference with polymorphic recursion brm/reading/p253- آ  type inference with polymorphic

Download Type inference with polymorphic recursion brm/reading/p253- آ  Type Inference with Polymorphic

Post on 14-Mar-2020

0 views

Category:

Documents

0 download

Embed Size (px)

TRANSCRIPT

  • Type Inference with Polymorphic Recursion

    FRITZ HENGLEIN

    University of Copenhagen

    The Damas-Milner Calculus is the typed A-calculus underlying the type system for ML and

    several other strongly typed polymorphic functional languages such as Mirandal and Haskell. Mycroft has extended its problematic monomorphic typing rule for recursive definitions with a

    polymorphic typing rule. He proved the resulting type system, which we call the Milner-Mycroft

    Calculus, sound with respect to Milner’s semantics, and showed that it preserves the principal typing property of the Damas-Milner Calculus. The extension is of practical significance in typed logic programming languages and, more generally, in any language with (mutually) recursive

    definitions.

    In this paper we show that the type inference problem for the Milner-Mycroft Calculus is log-space equivalent to semiunification, the problem of solving subsumption inequations between first-order terms. This result has been proved independently by Kfoury et al. In connection with the recently established undecidability of semiunification this implies that typability in the Milner-Mycroft Calculus is undecidable.

    We present some reasons why type inference with polymorphic recursion appears to be practical despite its undecidability. This also sheds some light on the observed practicality of ML in the face of recent theoretical intractability results.

    Finally, we exhibit a semiunification algorithm upon which a flexible, practical, and imple- mentable type inference algorithm for both Damas-Milner and Milner-Mycroft typing can be

    based.

    Categories and Subject Descriptors: D. 1.1 [Programming Techniques]: Applicative (Func- tional) Programming; D.3.3 [Programming Languages]: Language Constructs and Features—data types and structures; F.3.3 [Logics and Meanings of Programming]: Studies of Program Constructs—type structure; F.4. 1 [Mathematical Logic and Formal Langoages]: Mathematical Lo@c—lambda calculus and related systems

    General Terms: Algorithms, Design, Languages, Theory

    Additional Key Words and Phrases: Polymorphism, recursion, semiunification, type inference

    ‘M Miranda is a trademark of Research Software Limited.

    This research was performed at New York University (Courant Institute of the Mathematical

    Sciences) with support by the ONR under contract numbers NOO014-85-K-0413 and NOOO14-87-

    K-0461.

    Author’s address: University of Copenhagen, Universitet sparken 1, 2100 Copenhagen East,

    Denmark; email: henglein@diku.dk.

    Permission to copy without fee all or part of this material is granted provided that the copies are

    not made or distributed for direct commercial advantage, the ACM copyright notice and the title

    of the publication and its date appear, and notice is given that copying is by permission of the

    Association for Computing Machinery. To copy otherwise, or to republish, requires a fee and/or

    specific permission.

    Q 1993 ACM 0164–0925/93/0400–253 $01.50

    ACM Transactions on Programming Languages and Systems, Vol 15, No 2, April 1993, Pages 253–2S9

  • 254 . F. Henglein

    1. INTRODUCTION

    1.1 Polymorphic Recursion

    Recently designed languages such as (Standard) ML [52] try to combine the

    safety of compile-time type checking with the flexibility of declaration-less

    programming by inferring type information from the program rather than

    insisting on extensive declarations. ML’s type system, which we call the

    Damas-Milner Calculus, allows for definition and use of ( parametric) poly-

    morphic functions; that is, functions that operate uniformly on arguments

    that may range over a variety of types.

    A peculiarity in the Damas-Milner Calculus is that occurrences of a recur-

    sively defined function inside the body of its definition can only be used

    monomorphically (all of its occurrences have to have identically typed argu-

    ments and their results are typed identically), whereas occurrences outside

    its body can be used polymorphically (with arguments of different types). For

    this reason Mycroft [57] and independently Meertens [50] have suggested a

    polymorphic typing rule for recursive definitions that allows for polymorphic

    occurrences of the defined function in its body. Mycroft has shown that the

    resulting type system, termed the Milner-Mycroft Calculus here, is sound

    with respect to Milner’s semantics [51] and that the principal typing property

    of the Damas-Milner Calculus is preserved. The standard unification-based

    type inference algorithm is not complete for polymorphic recursion, though.

    Although the motivation for studying Mycroft’s extension to ML’s typing

    discipline may seem rather esoteric and of purely theoretical interest, it

    stems from practical considerations. In ML many typing problems at-

    tributable to the monomorphic recursive definition constraint can be avoided

    by appropriately nesting function definitions inside the scopes of previous

    definitions. Since ML provides polymorphically typed let-definitions-giving

    rise to the term let-polymorphism—nesting definitions is, indeed, a workable

    scheme in many cases. Some languages, however, do not provide nested

    scoping, but only top-level function (or procedure) definitions: e.g., ABC [18],

    SETL [63], and Prolog [64]. Consequently, all such top-level definitions

    combined have to be considered a single, generally mutually recursive defini-

    tion. Adopting ML’s monomorphic typing rule for recursive definitions in

    these languages precludes polymorphic usage of any defined function inside

    any definition. In particular, since logic programs, as observed in [58], can be

    viewed as massive mutually recursive definitions, using an ML-style type

    system would eliminate polymorphism from strongly typed logic program-

    ming languages almost completely. Mycroft’s extension, on the other hand,

    permits polymorphic usage in such a language setting.

    In many cases it is possible to investigate the dependency graph (“call

    graph) of mutually recursive definitions, process its maximal strong compo-

    nents in topological order, and treat them implicitly as polymorphically

    typed, nested let-definitions. But this is undesirable for several reasons:

    (1) The resulting typing discipline cannot be explained in a syntax-directed fashion, but is rather reminiscent of data-flow oriented reasoning. This

    ACM Transactions on Programmmg Languages and S~ stems, Vol 15, No 2, Aprd 1993

  • (2)

    Type Inference with Polymorphic Recursion . 255

    runs contrary to structured programming and program understanding. In

    particular, finding the source(s) of typing errors in the program text

    would be made even more difficult than the already problematic attribu-

    tion of type errors to source code in ML-like languages [33, 66].

    The topological processing does not completely capture the polymorphic

    typing rule. Mycroft reports a mutually recursive definition he encoun-

    tered in a “real life” programming project that could not be typed in ML,

    but could be typed by using the polymorphic typing rule for recursive

    definitions [57, Sect. 8]. Other, similar cases have been reported since.1

    1.2 Example

    Consider the following joint definition of functions map and squarelist in

    Standard ML, taken from [57].

    fun mapfl = if null 1 then nil else f (hd 1):: map f (tl 1) and

    squarelist 1 = map (fn x: int ~ x * x)1;

    As written this is a simultaneous definition of map and squarelist even

    though squarelist is not used in the definition of map. An ML type checker

    produces the types

    map: (int + int) + int list + int list

    squarelist: int list + int list

    due to ML’s monomorphic recursion rule even though we would expect, as

    sequential recursive definitions first of map and then of squarelist would

    yield, the type of map to be

    map: Va.V~. (ci - ~) X a list + ~ list.

    If we use map with an argument type different from int list we even get a

    type error.

    1.3 Outline of Paper

    In Section 2 we review the formal definition of the Milner-Mycroft Calculus

    along with the Damas-Milner Calculus, the typing system of the functional

    core of ML. Section 3 contains an introduction to semiunification, the problem

    of solving (equations and) subsumption inequations between first-order terms.

    In Section 4, which constitutes the technical core of this paper, type

    inference, and semiunification are formally connected: we show that typa-

    bility in the Milner-Mycroft Calculus and semiunification are log-space

    equivalent. The reduction of Milner-Mycroft typability to semiunification is

    presented in several steps. First, we formulate two syntax-directed type

    inference systems that are equivalent to the canonical type inference system

    for the Milner-Mycroft Calculus. Using the first-order version of the two, we

    show how to extract from a (possibly untypable) input program a system of

    equations and inequations between unquantified type expressions that char-

    acterizes typability (and more generally the typings) of the program. The

    lE g., on the ML mailing list.

    ACM Transactions on Programmmg Languages and Systems, Vol. 15, No. 2,

Recommended

View more >