Changes between Version 1 and Version 2 of Records/DeclaredOverloadedRecordFields


Ignore:
Timestamp:
Feb 17, 2012 10:28:08 PM (4 years ago)
Author:
guest
Comment:

--

Legend:

Unmodified
Added
Removed
Modified
  • Records/DeclaredOverloadedRecordFields

    v1 v2  
    1 ''' Declared Overloaded Record Fields (DORF) '''
     1= Declared Overloaded Record Fields (DORF) =
    22
    33
    44Explained in 5 wiki pages (these proposals are linked but somewhat orthogonal):
    5 No Mono Record Fields
    6 DORF -- Application Programmer's view
    7 DORF -- Implementor's view
    8 DORF -- Comparison to SORF
    9 Dot as Postfix Funcion Apply
    10 
    11 
    12 
    13 
    14 ------------------- No Mono Record Fields ---------------------------
     5
     6 * No Mono Record Fields   (precursor to DORF)
     7 * DORF -- Application Programmer's view
     8 * DORF -- Implementor's view
     9 * DORF -- Comparison to SORF
     10 * Dot as Postfix Funcion Apply   (optional syntactic sugar)
     11
     12
     13
     14
     15
     16== No Mono Record Fields ==
    1517
    1618This proposal is a precursor to overloaded record fields.
     
    3739    data T = MkT { x, y :: Int }
    3840}}}
    39 then the existence of field `y' is hidden;
    40 type T and field label `x' are exported, but not data constructor MkT, so `x' is unusable.
    41 
    42 (Without the ‑XNoMonoRecordFields flag, field selector function x would be exported.)
    43 
    44 
    45 
    46 
    47 ----------------- Declared Overloaded Record Fields (DORF) --------
    48 ----------------- Application Programmer's view -------------------
     41then the existence of field `y` is hidden;
     42type `T` and field label `x` are exported, but not data constructor `MkT`, so `x` is unusable.
     43
     44(Without the ‑XNoMonoRecordFields flag, field selector function `x` would be exported.)
     45
     46
     47
     48
     49== Declared Overloaded Record Fields (DORF) ==
     50== Application Programmer's view ==
    4951
    5052This proposal is addressing the "narrow issue" of namespacing for record field names.
     
    5860
    5961Currently in Haskell two records in the same module can't share a field name. This is because declaring a field name within a data decl creates a monomorphic selector function; and if it's monomorphic, we can only have one. I think the wiki is characterising the problem incorrectly:
    60 * it's _not_ that the field name appearing in different record decls
    61   is ambiguous between the two record types and we need some
    62   (syntactical) way of choosing between the different definitions;
    63 
    64 * rather, we have one field name, and we lack the syntax/semantics for
    65   sharing it between different records.
     62
     63 * it's __not__ that the field name appearing in different record decls is ambiguous between the two record types
     64   so we need some (syntactical) way of choosing between the different definitions;
     65
     66
     67 * rather, we have one field name, and we lack the syntax/semantics for sharing it between different records.
    6668
    6769An example: let's say I have a database application with a field (meaning type) customer_id. Then it appears in records for name and address, pricing, order entry, etc. This is not a name 'clash', it's 'intended sharing'. (It really galls me to even put it that way for explanatory purposes. Really it's the **same** customer_id.)
    6870In data model design you'd typically go about identifying all the fields (types aka attributes) and putting them in a data dictionary. Then you'd construct your records from them. You might (possibly) put the data dictionary in a distinct module, for easy maintenance. But you'd certainly want all the customer-related records in the same module. So a data decl:
     71{{{
    6972    data Customer_NameAddress = Cust_NA { customer_id :: Int, ... }
     73}}}
    7074is _not_ declaring customer_id, it's _using_ (or instancing) an already-declared field for customer_id.
    7175Similarly, if I have a family of objects, all with a `reset' method, that's not umpteen methods with a 'clash' of names, it's one method with umpteen instances. (And I might create a family of record structures to describe each object, and store the `reset' method within it.)
    7276
    7377What's more, the Haskell 98 field selector (auto-created from the data decl) is half-way to what we want. It's a function:
    74 
     78{{{
    7579    customer_id :: Customer_NameAddress -> Int
    76 
     80}}}
    7781The DORF proposal generalises that signature: if you want to share a field across different records, its selector function needs to be overloaded to this type:
    7882
    7983    customer_id :: r{ customer_id :: Int } => r -> Int
    8084
    81 The r{ ... } is syntactic sugar for the constraint meaning "record r has field customer_id at type Int".
     85The 'r{ ... }' is syntactic sugar for the constraint meaning "record r has field customer_id at type Int".
    8286
    8387We need a way to declare that a name is available as an overloadable field name (roughly speaking, a class/method definition), proposed syntax: