Skip to content

Inference: a section over a fully-specced user function doesn't infer its type in a no-expected-type position #76

Description

@hierophantos

Summary

A partial application (section) over a user function whose signature is fully known fails to synthesize its type when there is no expected type from context (e.g. a bare def := …). The same partial works everywhere an expected type is supplied. The section case is the compelling one: the hole's type is fully determined by the function's spec, so it should synthesize without needing an annotation.

Repro (HEAD 4e56da1d, via process-file)

spec pow Int Int -> Int
defn pow [x n]
  match n
    | 0 -> 1
    | _ -> * x [pow x .(n - 1)]

;; WORKS — an expected type is supplied:
pow 2 10                              ;; => 1024
map [pow 2 _] '[1 2 3 4]              ;; => '[2 4 8 16]   (map checks the arg against [A -> B])
[pow 2 _] 3                           ;; => 8            (applied directly)
def k : <Int -> Int> := [pow 2 _]    ;; k 5 => 32       (annotated)

;; FAILS — no expected type:
def g := [pow 2 _]                    ;; ERROR: Could not infer type
def f := [fn [x] [pow 2 x]]           ;; ERROR: Could not infer type

Diagnosis

The failure is specific to the pure-synthesis position (no expected type):

  • Section [pow 2 _] — the hole type is fully determined by pow's spec (Int), so a section over a fully-specced function should synthesize Int -> Int on its own. This is the gap to close.
  • Unannotated lambda [fn [x] [pow 2 x]] — deriving the domain from the body's use of a specced function is the more standard "synthesis needs annotation-or-expected-type" limitation (lower priority; may be by-design).

Contrast: keyword-operator sections ([+ _ 1]) do work in synthesis position (from the N6e first-class-ops arc); user-function sections do not.

Related (minor)

A function type in a def/the annotation must use angle brackets <Int -> Int>; the square-bracket form [Int -> Int] silently mis-parses as application and yields a confusing "Unbound variable" error. A clearer diagnostic (or accepting [T -> T]) would help.

Notes

  • Owner-confirmed the section-over-a-fully-specced-function case should be made to work.
  • On the same first-class-ops surface as the N6e arc.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions