Skip to content

Instantly share code, notes, and snippets.

@MonoidMusician
Created February 28, 2018 16:48
Show Gist options
  • Save MonoidMusician/9fbeb4ac3d92e840c339fd5e22e15c66 to your computer and use it in GitHub Desktop.
Save MonoidMusician/9fbeb4ac3d92e840c339fd5e22e15c66 to your computer and use it in GitHub Desktop.
The best merge functions around!
module Merging where
import Type.Row (class ListToRow, class RowListNub, class RowToList)
{-
exports.unsafeMerge = function(r1) {
return function(r2) {
var r = {};
for (var k1 in r2) {
if ({}.hasOwnProperty.call(r2, k1)) {
r[k1] = r2[k1];
}
}
for (var k2 in r1) {
if ({}.hasOwnProperty.call(r1, k2)) {
r[k2] = r1[k2];
}
}
return r;
}
}
-}
foreign import unsafeMerge :: forall r1 r2 r3. Record r1 -> Record r2 -> Record r3
badMerge :: forall l r u. Union l r u => {|l} -> {|r} -> {|u}
badMerge = unsafeMerge
-- | A left-biased (well-typed!) merge function that
merge ::
forall l r u ul ul' u'.
Union l r u =>
RowToList u ul =>
RowListNub ul ul' =>
ListToRow ul' u' =>
{|l} -> {|r} -> {|u'}
merge = unsafeMerge
-- | Same as `merge` but assumes that the input records are disjoint for better
-- | inference properties.
merge' ::
forall l r u ul.
Union l r u =>
RowToList u ul =>
RowListNub ul ul =>
ListToRow ul u =>
{|l} -> {|r} -> {|u}
merge' = merge
{-
Hole 'help' has the inferred type
{ b :: Int
}
in value declaration test
-}
-- test :: {a :: Int, b :: Int}
-- test = merge' {a:0} ?help
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment