From 79792730843af7ffbab63c2819c7c88abd95ea4d Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sat, 7 Dec 2019 19:11:15 +0100 Subject: [PATCH 01/23] Use strict types for applicatives --- src/FSharpPlus/Functor.fs | 46 ++++++++++++++++++++------------------- 1 file changed, 24 insertions(+), 22 deletions(-) diff --git a/src/FSharpPlus/Functor.fs b/src/FSharpPlus/Functor.fs index 534508cd3..4e582ea33 100644 --- a/src/FSharpPlus/Functor.fs +++ b/src/FSharpPlus/Functor.fs @@ -139,35 +139,32 @@ type Return = type Apply = inherit Default1 - - static member inline ``<*>`` (f: '``Monad<'T->'U>`` , x: '``Monad<'T>`` , []_output: '``Monad<'U>`` , []_mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) - static member inline ``<*>`` (f: '``Applicative<'T->'U>``, x: '``Applicative<'T>``, []_output: '``Applicative<'U>``, []_mthd:Default1) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) f, x) - static member ``<*>`` (f: Lazy<'T->'U> , x: Lazy<'T> , []_output: Lazy<'U> , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> - static member ``<*>`` (f: seq<_> , x: seq<'T> , []_output: seq<'U> , []_mthd: Apply) = Seq.apply f x : seq<'U> + static member ``<*>`` ((f: Lazy<'T->'U> , x: Lazy<'T> , _output: Lazy<'U>) , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> + static member ``<*>`` ((f: seq<_> , x: seq<'T> , _output: seq<'U>) , []_mthd: Apply) = Seq.apply f x : seq<'U> #if !FABLE_COMPILER - static member ``<*>`` (f: IEnumerator<_> , x: IEnumerator<'T> , []_output: IEnumerator<'U> , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> + static member ``<*>`` ((f: IEnumerator<_> , x: IEnumerator<'T> , _output: IEnumerator<'U>) , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> #endif - static member ``<*>`` (f: list<_> , x: list<'T> , []_output: list<'U> , []_mthd: Apply) = List.apply f x : list<'U> - static member ``<*>`` (f: _ [] , x: 'T [] , []_output: 'U [] , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] - static member ``<*>`` (f: 'r -> _ , g: _ -> 'T , []_output: 'r -> 'U , []_mthd: Apply) = fun x -> f x (g x) : 'U - static member inline ``<*>`` ((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , []_output: 'Monoid * 'U , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U + static member ``<*>`` ((f: list<_> , x: list<'T> , _output: list<'U>) , []_mthd: Apply) = List.apply f x : list<'U> + static member ``<*>`` ((f: _ [] , x: 'T [] , _output: 'U []) , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] + static member ``<*>`` ((f: 'r -> _ , g: _ -> 'T , _output: 'r -> 'U) , []_mthd: Apply) = fun x -> f x (g x) : 'U + static member inline ``<*>`` (((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , _output: 'Monoid * 'U) , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U #if !FABLE_COMPILER - static member ``<*>`` (f: Task<_> , x: Task<'T> , []_output: Task<'U> , []_mthd: Apply) = Task.apply f x : Task<'U> + static member ``<*>`` ((f: Task<_> , x: Task<'T> , _output: Task<'U>) , []_mthd: Apply) = Task.apply f x : Task<'U> #endif - static member ``<*>`` (f: Async<_> , x: Async<'T> , []_output: Async<'U> , []_mthd: Apply) = Async.apply f x : Async<'U> - static member ``<*>`` (f: option<_> , x: option<'T> , []_output: option<'U> , []_mthd: Apply) = Option.apply f x : option<'U> - static member ``<*>`` (f: Result<_,'E> , x: Result<'T,'E> , []_output: Result<'b,'E> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> - static member ``<*>`` (f: Choice<_,'E> , x: Choice<'T,'E> , []_output: Choice<'b,'E> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> - static member inline ``<*>`` (KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), []_output: KeyValuePair<'Key,'U>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) + static member ``<*>`` ((f: Async<_> , x: Async<'T> , _output: Async<'U>) , []_mthd: Apply) = Async.apply f x : Async<'U> + static member ``<*>`` ((f: option<_> , x: option<'T> , _output: option<'U>) , []_mthd: Apply) = Option.apply f x : option<'U> + static member ``<*>`` ((f: Result<_,'E> , x: Result<'T,'E> , _output: Result<'b,'E>) , []_mthd: Apply) = Result.apply f x : Result<'U,'E> + static member ``<*>`` ((f: Choice<_,'E> , x: Choice<'T,'E> , _output: Choice<'b,'E>) , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> + static member inline ``<*>`` ((KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), _output: KeyValuePair<'Key,'U>), []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) - static member ``<*>`` (f: Map<'Key,_> , x: Map<'Key,'T> , []_output: Map<'Key,'U> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { + static member ``<*>`` ((f: Map<'Key,_> , x: Map<'Key,'T> , _output: Map<'Key,'U>) , []_mthd: Apply) : Map<'Key,'U> = Map (seq { for KeyValue(k, vf) in f do match Map.tryFind k x with | Some vx -> yield k, vf vx | _ -> () }) - static member ``<*>`` (f: Dictionary<'Key,_>, x: Dictionary<'Key,'T> , []_output: Dictionary<'Key,'U> , []_mthd: Apply) : Dictionary<'Key,'U> = + static member ``<*>`` ((f: Dictionary<'Key,_>, x: Dictionary<'Key,'T> , _output: Dictionary<'Key,'U>) , []_mthd: Apply) : Dictionary<'Key,'U> = let dct = Dictionary () for KeyValue(k, vf) in f do match x.TryGetValue k with @@ -176,19 +173,24 @@ type Apply = dct #if !FABLE_COMPILER - static member ``<*>`` (f: Expr<'T->'U>, x: Expr<'T>, []_output: Expr<'U>, []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) + static member ``<*>`` ((f: Expr<'T->'U>, x: Expr<'T>, _output: Expr<'U>), []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) #endif - static member ``<*>`` (f: ('T->'U) ResizeArray, x: 'T ResizeArray, []_output: 'U ResizeArray, []_mthd: Apply) = + static member ``<*>`` ((f: ('T->'U) ResizeArray, x: 'T ResizeArray, _output: 'U ResizeArray), []_mthd: Apply) = ResizeArray (Seq.collect (fun x1 -> Seq.collect (fun x2 -> Seq.singleton (x1 x2)) x) f) : 'U ResizeArray static member inline Invoke (f: '``Applicative<'T -> 'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = - ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_ -> _) input1, input2, output, mthd) + ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : (_*_*_)*_ -> _) (input1, input2, output), mthd) call(Unchecked.defaultof, f, x, Unchecked.defaultof<'``Applicative<'U>``>) static member inline InvokeOnInstance (f: '``Applicative<'T->'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) (f, x)) +type Apply with + static member inline ``<*>`` ((f: '``Monad<'T->'U>`` , x: '``Monad<'T>`` , _output: '``Monad<'U>`` ), []_mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) + static member inline ``<*>`` ((_: ^t when ^t : null and ^t: struct, _: ^u when ^u : null and ^u: struct, _output: ^r when ^r : null and ^r: struct), _mthd: Default1) = id + static member inline ``<*>`` ((f: '``Applicative<'T->'U>``, x: '``Applicative<'T>``, _output: '``Applicative<'U>``), []_mthd:Default1) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) f, x) + // Functor class ---------------------------------------------------------- type Iterate = @@ -900,4 +902,4 @@ module internal MonadOps = #endif let inline (<*>) f x = Apply.Invoke f x let inline (<|>) x y = Append.Invoke x y - let inline (>=>) (f: 'a->'``Monad<'b>``) (g: 'b->'``Monad<'c>``) (x: 'a) : '``Monad<'c>`` = f x >>= g \ No newline at end of file + let inline (>=>) (f: 'a->'``Monad<'b>``) (g: 'b->'``Monad<'c>``) (x: 'a) : '``Monad<'c>`` = f x >>= g From 0177fb6d3879d7956b4f75c01f7b808c97c71c86 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sat, 7 Dec 2019 23:02:05 +0100 Subject: [PATCH 02/23] Ambiguate KeyValuePair with struct tuple --- src/FSharpPlus/Functor.fs | 1 + 1 file changed, 1 insertion(+) diff --git a/src/FSharpPlus/Functor.fs b/src/FSharpPlus/Functor.fs index 4e582ea33..c0669e439 100644 --- a/src/FSharpPlus/Functor.fs +++ b/src/FSharpPlus/Functor.fs @@ -157,6 +157,7 @@ type Apply = static member ``<*>`` ((f: Result<_,'E> , x: Result<'T,'E> , _output: Result<'b,'E>) , []_mthd: Apply) = Result.apply f x : Result<'U,'E> static member ``<*>`` ((f: Choice<_,'E> , x: Choice<'T,'E> , _output: Choice<'b,'E>) , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> static member inline ``<*>`` ((KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), _output: KeyValuePair<'Key,'U>), []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) + static member inline ``<*>`` ((struct (a: 'Monoid, f), struct (b: 'Monoid, x: 'T), _output: struct ('Monoid * 'U)), []_mthd: Apply) = struct (FSharpPlus.Control.Plus.Invoke a b, f x) static member ``<*>`` ((f: Map<'Key,_> , x: Map<'Key,'T> , _output: Map<'Key,'U>) , []_mthd: Apply) : Map<'Key,'U> = Map (seq { for KeyValue(k, vf) in f do From e43fb5bfaeb49ca3afd82d28b0b7c150a8012e35 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sun, 8 Dec 2019 00:29:20 +0100 Subject: [PATCH 03/23] Try not including the first arg in the tupling See if type inference improves like this --- src/FSharpPlus/Functor.fs | 46 +++++++++++++++++++-------------------- 1 file changed, 23 insertions(+), 23 deletions(-) diff --git a/src/FSharpPlus/Functor.fs b/src/FSharpPlus/Functor.fs index c0669e439..a4ad16de7 100644 --- a/src/FSharpPlus/Functor.fs +++ b/src/FSharpPlus/Functor.fs @@ -140,32 +140,32 @@ type Return = type Apply = inherit Default1 - static member ``<*>`` ((f: Lazy<'T->'U> , x: Lazy<'T> , _output: Lazy<'U>) , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> - static member ``<*>`` ((f: seq<_> , x: seq<'T> , _output: seq<'U>) , []_mthd: Apply) = Seq.apply f x : seq<'U> + static member ``<*>`` (f: Lazy<'T->'U> , (x: Lazy<'T> , _output: Lazy<'U>) , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> + static member ``<*>`` (f: seq<_> , (x: seq<'T> , _output: seq<'U>) , []_mthd: Apply) = Seq.apply f x : seq<'U> #if !FABLE_COMPILER - static member ``<*>`` ((f: IEnumerator<_> , x: IEnumerator<'T> , _output: IEnumerator<'U>) , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> + static member ``<*>`` (f: IEnumerator<_> , (x: IEnumerator<'T> , _output: IEnumerator<'U>) , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> #endif - static member ``<*>`` ((f: list<_> , x: list<'T> , _output: list<'U>) , []_mthd: Apply) = List.apply f x : list<'U> - static member ``<*>`` ((f: _ [] , x: 'T [] , _output: 'U []) , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] - static member ``<*>`` ((f: 'r -> _ , g: _ -> 'T , _output: 'r -> 'U) , []_mthd: Apply) = fun x -> f x (g x) : 'U - static member inline ``<*>`` (((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , _output: 'Monoid * 'U) , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U + static member ``<*>`` (f: list<_> , (x: list<'T> , _output: list<'U>) , []_mthd: Apply) = List.apply f x : list<'U> + static member ``<*>`` (f: _ [] , (x: 'T [] , _output: 'U []) , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] + static member ``<*>`` (f: 'r -> _ , (g: _ -> 'T , _output: 'r -> 'U) , []_mthd: Apply) = fun x -> f x (g x) : 'U + static member inline ``<*>`` ((a: 'Monoid, f) , ((b: 'Monoid, x: 'T) , _output: 'Monoid * 'U) , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U #if !FABLE_COMPILER - static member ``<*>`` ((f: Task<_> , x: Task<'T> , _output: Task<'U>) , []_mthd: Apply) = Task.apply f x : Task<'U> + static member ``<*>`` (f: Task<_> , (x: Task<'T> , _output: Task<'U>) , []_mthd: Apply) = Task.apply f x : Task<'U> #endif - static member ``<*>`` ((f: Async<_> , x: Async<'T> , _output: Async<'U>) , []_mthd: Apply) = Async.apply f x : Async<'U> - static member ``<*>`` ((f: option<_> , x: option<'T> , _output: option<'U>) , []_mthd: Apply) = Option.apply f x : option<'U> - static member ``<*>`` ((f: Result<_,'E> , x: Result<'T,'E> , _output: Result<'b,'E>) , []_mthd: Apply) = Result.apply f x : Result<'U,'E> - static member ``<*>`` ((f: Choice<_,'E> , x: Choice<'T,'E> , _output: Choice<'b,'E>) , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> - static member inline ``<*>`` ((KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), _output: KeyValuePair<'Key,'U>), []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) - static member inline ``<*>`` ((struct (a: 'Monoid, f), struct (b: 'Monoid, x: 'T), _output: struct ('Monoid * 'U)), []_mthd: Apply) = struct (FSharpPlus.Control.Plus.Invoke a b, f x) - - static member ``<*>`` ((f: Map<'Key,_> , x: Map<'Key,'T> , _output: Map<'Key,'U>) , []_mthd: Apply) : Map<'Key,'U> = Map (seq { + static member ``<*>`` (f: Async<_> , (x: Async<'T> , _output: Async<'U>) , []_mthd: Apply) = Async.apply f x : Async<'U> + static member ``<*>`` (f: option<_> , (x: option<'T> , _output: option<'U>) , []_mthd: Apply) = Option.apply f x : option<'U> + static member ``<*>`` (f: Result<_,'E> , (x: Result<'T,'E> , _output: Result<'b,'E>) , []_mthd: Apply) = Result.apply f x : Result<'U,'E> + static member ``<*>`` (f: Choice<_,'E> , (x: Choice<'T,'E> , _output: Choice<'b,'E>) , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> + static member inline ``<*>`` (KeyValue(a: 'Key, f), (KeyValue(b: 'Key, x: 'T), _output: KeyValuePair<'Key,'U>), []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) + static member inline ``<*>`` (struct (a: 'Monoid, f), (struct (b: 'Monoid, x: 'T), _output: struct ('Monoid * 'U)), []_mthd: Apply) = struct (FSharpPlus.Control.Plus.Invoke a b, f x) + + static member ``<*>`` (f: Map<'Key,_> , (x: Map<'Key,'T> , _output: Map<'Key,'U>) , []_mthd: Apply) : Map<'Key,'U> = Map (seq { for KeyValue(k, vf) in f do match Map.tryFind k x with | Some vx -> yield k, vf vx | _ -> () }) - static member ``<*>`` ((f: Dictionary<'Key,_>, x: Dictionary<'Key,'T> , _output: Dictionary<'Key,'U>) , []_mthd: Apply) : Dictionary<'Key,'U> = + static member ``<*>`` (f: Dictionary<'Key,_>, (x: Dictionary<'Key,'T> , _output: Dictionary<'Key,'U>) , []_mthd: Apply) : Dictionary<'Key,'U> = let dct = Dictionary () for KeyValue(k, vf) in f do match x.TryGetValue k with @@ -174,23 +174,23 @@ type Apply = dct #if !FABLE_COMPILER - static member ``<*>`` ((f: Expr<'T->'U>, x: Expr<'T>, _output: Expr<'U>), []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) + static member ``<*>`` (f: Expr<'T->'U>, (x: Expr<'T>, _output: Expr<'U>), []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) #endif - static member ``<*>`` ((f: ('T->'U) ResizeArray, x: 'T ResizeArray, _output: 'U ResizeArray), []_mthd: Apply) = + static member ``<*>`` (f: ('T->'U) ResizeArray, (x: 'T ResizeArray, _output: 'U ResizeArray), []_mthd: Apply) = ResizeArray (Seq.collect (fun x1 -> Seq.collect (fun x2 -> Seq.singleton (x1 x2)) x) f) : 'U ResizeArray static member inline Invoke (f: '``Applicative<'T -> 'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = - ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : (_*_*_)*_ -> _) (input1, input2, output), mthd) + ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*(_*_)*_ -> _) input1, (input2, output), mthd) call(Unchecked.defaultof, f, x, Unchecked.defaultof<'``Applicative<'U>``>) static member inline InvokeOnInstance (f: '``Applicative<'T->'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) (f, x)) type Apply with - static member inline ``<*>`` ((f: '``Monad<'T->'U>`` , x: '``Monad<'T>`` , _output: '``Monad<'U>`` ), []_mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) - static member inline ``<*>`` ((_: ^t when ^t : null and ^t: struct, _: ^u when ^u : null and ^u: struct, _output: ^r when ^r : null and ^r: struct), _mthd: Default1) = id - static member inline ``<*>`` ((f: '``Applicative<'T->'U>``, x: '``Applicative<'T>``, _output: '``Applicative<'U>``), []_mthd:Default1) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) f, x) + static member inline ``<*>`` (f: '``Monad<'T->'U>`` , (x: '``Monad<'T>`` , _output: '``Monad<'U>`` ), []_mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) + static member inline ``<*>`` (_: ^t when ^t : null and ^t: struct, (_: ^u when ^u : null and ^u: struct, _output: ^r when ^r : null and ^r: struct), _mthd: Default1) = id + static member inline ``<*>`` (f: '``Applicative<'T->'U>``, (x: '``Applicative<'T>``, _output: '``Applicative<'U>``), []_mthd:Default1) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) f, x) // Functor class ---------------------------------------------------------- From 669e85038299a4e71e8722fb8cd42a186cbff200 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sun, 8 Dec 2019 10:06:54 +0100 Subject: [PATCH 04/23] Use an option in the output only --- src/FSharpPlus/Functor.fs | 46 +++++++++++++++++++-------------------- 1 file changed, 23 insertions(+), 23 deletions(-) diff --git a/src/FSharpPlus/Functor.fs b/src/FSharpPlus/Functor.fs index a4ad16de7..4bd9b51d4 100644 --- a/src/FSharpPlus/Functor.fs +++ b/src/FSharpPlus/Functor.fs @@ -140,32 +140,32 @@ type Return = type Apply = inherit Default1 - static member ``<*>`` (f: Lazy<'T->'U> , (x: Lazy<'T> , _output: Lazy<'U>) , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> - static member ``<*>`` (f: seq<_> , (x: seq<'T> , _output: seq<'U>) , []_mthd: Apply) = Seq.apply f x : seq<'U> + static member ``<*>`` (f: Lazy<'T->'U> , x: Lazy<'T> , _output: Option> , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> + static member ``<*>`` (f: seq<_> , x: seq<'T> , _output: Option> , []_mthd: Apply) = Seq.apply f x : seq<'U> #if !FABLE_COMPILER - static member ``<*>`` (f: IEnumerator<_> , (x: IEnumerator<'T> , _output: IEnumerator<'U>) , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> + static member ``<*>`` (f: IEnumerator<_> , x: IEnumerator<'T> , _output: Option> , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> #endif - static member ``<*>`` (f: list<_> , (x: list<'T> , _output: list<'U>) , []_mthd: Apply) = List.apply f x : list<'U> - static member ``<*>`` (f: _ [] , (x: 'T [] , _output: 'U []) , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] - static member ``<*>`` (f: 'r -> _ , (g: _ -> 'T , _output: 'r -> 'U) , []_mthd: Apply) = fun x -> f x (g x) : 'U - static member inline ``<*>`` ((a: 'Monoid, f) , ((b: 'Monoid, x: 'T) , _output: 'Monoid * 'U) , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U + static member ``<*>`` (f: list<_> , x: list<'T> , _output: Option> , []_mthd: Apply) = List.apply f x : list<'U> + static member ``<*>`` (f: _ [] , x: 'T [] , _output: Option<'U []> , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] + static member ``<*>`` (f: 'r -> _ , g: _ -> 'T , _output: Option< 'r -> 'U> , []_mthd: Apply) = fun x -> f x (g x) : 'U + static member inline ``<*>`` ((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , _output: Option<'Monoid * 'U> , []_mthd: Apply) = (FSharpPlus.Control.Plus.Invoke a b, f x) : 'Monoid *'U #if !FABLE_COMPILER - static member ``<*>`` (f: Task<_> , (x: Task<'T> , _output: Task<'U>) , []_mthd: Apply) = Task.apply f x : Task<'U> + static member ``<*>`` (f: Task<_> , x: Task<'T> , _output: Option> , []_mthd: Apply) = Task.apply f x : Task<'U> #endif - static member ``<*>`` (f: Async<_> , (x: Async<'T> , _output: Async<'U>) , []_mthd: Apply) = Async.apply f x : Async<'U> - static member ``<*>`` (f: option<_> , (x: option<'T> , _output: option<'U>) , []_mthd: Apply) = Option.apply f x : option<'U> - static member ``<*>`` (f: Result<_,'E> , (x: Result<'T,'E> , _output: Result<'b,'E>) , []_mthd: Apply) = Result.apply f x : Result<'U,'E> - static member ``<*>`` (f: Choice<_,'E> , (x: Choice<'T,'E> , _output: Choice<'b,'E>) , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> - static member inline ``<*>`` (KeyValue(a: 'Key, f), (KeyValue(b: 'Key, x: 'T), _output: KeyValuePair<'Key,'U>), []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) - static member inline ``<*>`` (struct (a: 'Monoid, f), (struct (b: 'Monoid, x: 'T), _output: struct ('Monoid * 'U)), []_mthd: Apply) = struct (FSharpPlus.Control.Plus.Invoke a b, f x) - - static member ``<*>`` (f: Map<'Key,_> , (x: Map<'Key,'T> , _output: Map<'Key,'U>) , []_mthd: Apply) : Map<'Key,'U> = Map (seq { + static member ``<*>`` (f: Async<_> , x: Async<'T> , _output: Option> , []_mthd: Apply) = Async.apply f x : Async<'U> + static member ``<*>`` (f: option<_> , x: option<'T> , _output: Option> , []_mthd: Apply) = Option.apply f x : option<'U> + static member ``<*>`` (f: Result<_,'E> , x: Result<'T,'E> , _output: Option> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> + static member ``<*>`` (f: Choice<_,'E> , x: Choice<'T,'E> , _output: Option> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> + static member inline ``<*>`` (KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), _output: Option>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (FSharpPlus.Control.Plus.Invoke a b, f x) + static member inline ``<*>`` (struct (a: 'Monoid, f), struct (b: 'Monoid, x: 'T), _output: Option, []_mthd: Apply) = struct (FSharpPlus.Control.Plus.Invoke a b, f x) + + static member ``<*>`` (f: Map<'Key,_> , x: Map<'Key,'T> , _output: Option> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { for KeyValue(k, vf) in f do match Map.tryFind k x with | Some vx -> yield k, vf vx | _ -> () }) - static member ``<*>`` (f: Dictionary<'Key,_>, (x: Dictionary<'Key,'T> , _output: Dictionary<'Key,'U>) , []_mthd: Apply) : Dictionary<'Key,'U> = + static member ``<*>`` (f: Dictionary<'Key,_>, x: Dictionary<'Key,'T> , _output: Option> , []_mthd: Apply) : Dictionary<'Key,'U> = let dct = Dictionary () for KeyValue(k, vf) in f do match x.TryGetValue k with @@ -174,23 +174,23 @@ type Apply = dct #if !FABLE_COMPILER - static member ``<*>`` (f: Expr<'T->'U>, (x: Expr<'T>, _output: Expr<'U>), []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) + static member ``<*>`` (f: Expr<'T->'U>, x: Expr<'T>, _output: Option>, []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) #endif - static member ``<*>`` (f: ('T->'U) ResizeArray, (x: 'T ResizeArray, _output: 'U ResizeArray), []_mthd: Apply) = + static member ``<*>`` (f: ('T->'U) ResizeArray, x: 'T ResizeArray, _output: Option<'U ResizeArray>, []_mthd: Apply) = ResizeArray (Seq.collect (fun x1 -> Seq.collect (fun x2 -> Seq.singleton (x1 x2)) x) f) : 'U ResizeArray static member inline Invoke (f: '``Applicative<'T -> 'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = - ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*(_*_)*_ -> _) input1, (input2, output), mthd) + ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_ -> _) input1, input2, Some output, mthd) call(Unchecked.defaultof, f, x, Unchecked.defaultof<'``Applicative<'U>``>) static member inline InvokeOnInstance (f: '``Applicative<'T->'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) (f, x)) type Apply with - static member inline ``<*>`` (f: '``Monad<'T->'U>`` , (x: '``Monad<'T>`` , _output: '``Monad<'U>`` ), []_mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) - static member inline ``<*>`` (_: ^t when ^t : null and ^t: struct, (_: ^u when ^u : null and ^u: struct, _output: ^r when ^r : null and ^r: struct), _mthd: Default1) = id - static member inline ``<*>`` (f: '``Applicative<'T->'U>``, (x: '``Applicative<'T>``, _output: '``Applicative<'U>``), []_mthd:Default1) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) f, x) + static member inline ``<*>`` (f: '``Monad<'T->'U>`` , x: '``Monad<'T>`` , _output: Option<'``Monad<'U>``> , _mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) + static member inline ``<*>`` (_: ^t when ^t : null and ^t: struct, _: ^u when ^u : null and ^u: struct, _output: Option< ^r> when ^r : null and ^r: struct, _mthd: Default1) = id + static member inline ``<*>`` (f: '``Applicative<'T->'U>``, x: '``Applicative<'T>`` , _output: Option<'``Applicative<'U>`` > , _mthd:Default1) : '``Applicative<'U>`` = Apply.InvokeOnInstance f x // Functor class ---------------------------------------------------------- From cb2f49fb076278d4d0d9614d0f49492a0e569865 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sun, 8 Dec 2019 12:12:51 +0100 Subject: [PATCH 05/23] Use Id --- src/FSharpPlus/Functor.fs | 48 +++++++++++++++++++-------------------- 1 file changed, 24 insertions(+), 24 deletions(-) diff --git a/src/FSharpPlus/Functor.fs b/src/FSharpPlus/Functor.fs index 4bd9b51d4..a8fb7b7bc 100644 --- a/src/FSharpPlus/Functor.fs +++ b/src/FSharpPlus/Functor.fs @@ -140,32 +140,32 @@ type Return = type Apply = inherit Default1 - static member ``<*>`` (f: Lazy<'T->'U> , x: Lazy<'T> , _output: Option> , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> - static member ``<*>`` (f: seq<_> , x: seq<'T> , _output: Option> , []_mthd: Apply) = Seq.apply f x : seq<'U> + static member ``<*>`` (f: Lazy<'T->'U> , x: Lazy<'T> , _output: Id> , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> + static member ``<*>`` (f: seq<_> , x: seq<'T> , _output: Id> , []_mthd: Apply) = Seq.apply f x : seq<'U> #if !FABLE_COMPILER - static member ``<*>`` (f: IEnumerator<_> , x: IEnumerator<'T> , _output: Option> , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> + static member ``<*>`` (f: IEnumerator<_> , x: IEnumerator<'T> , _output: Id> , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> #endif - static member ``<*>`` (f: list<_> , x: list<'T> , _output: Option> , []_mthd: Apply) = List.apply f x : list<'U> - static member ``<*>`` (f: _ [] , x: 'T [] , _output: Option<'U []> , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] - static member ``<*>`` (f: 'r -> _ , g: _ -> 'T , _output: Option< 'r -> 'U> , []_mthd: Apply) = fun x -> f x (g x) : 'U - static member inline ``<*>`` ((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , _output: Option<'Monoid * 'U> , []_mthd: Apply) = (FSharpPlus.Control.Plus.Invoke a b, f x) : 'Monoid *'U + static member ``<*>`` (f: list<_> , x: list<'T> , _output: Id> , []_mthd: Apply) = List.apply f x : list<'U> + static member ``<*>`` (f: _ [] , x: 'T [] , _output: Id<'U []> , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] + static member ``<*>`` (f: 'r -> _ , g: _ -> 'T , _output: Id< 'r -> 'U> , []_mthd: Apply) = fun x -> f x (g x) : 'U + static member inline ``<*>`` ((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , _output: Id<'Monoid * 'U> , []_mthd: Apply) = (FSharpPlus.Control.Plus.Invoke a b, f x) : 'Monoid *'U #if !FABLE_COMPILER - static member ``<*>`` (f: Task<_> , x: Task<'T> , _output: Option> , []_mthd: Apply) = Task.apply f x : Task<'U> + static member ``<*>`` (f: Task<_> , x: Task<'T> , _output: Id> , []_mthd: Apply) = Task.apply f x : Task<'U> #endif - static member ``<*>`` (f: Async<_> , x: Async<'T> , _output: Option> , []_mthd: Apply) = Async.apply f x : Async<'U> - static member ``<*>`` (f: option<_> , x: option<'T> , _output: Option> , []_mthd: Apply) = Option.apply f x : option<'U> - static member ``<*>`` (f: Result<_,'E> , x: Result<'T,'E> , _output: Option> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> - static member ``<*>`` (f: Choice<_,'E> , x: Choice<'T,'E> , _output: Option> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> - static member inline ``<*>`` (KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), _output: Option>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (FSharpPlus.Control.Plus.Invoke a b, f x) - static member inline ``<*>`` (struct (a: 'Monoid, f), struct (b: 'Monoid, x: 'T), _output: Option, []_mthd: Apply) = struct (FSharpPlus.Control.Plus.Invoke a b, f x) - - static member ``<*>`` (f: Map<'Key,_> , x: Map<'Key,'T> , _output: Option> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { + static member ``<*>`` (f: Async<_> , x: Async<'T> , _output: Id> , []_mthd: Apply) = Async.apply f x : Async<'U> + static member ``<*>`` (f: option<_> , x: option<'T> , _output: Id> , []_mthd: Apply) = Option.apply f x : option<'U> + static member ``<*>`` (f: Result<_,'E> , x: Result<'T,'E> , _output: Id> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> + static member ``<*>`` (f: Choice<_,'E> , x: Choice<'T,'E> , _output: Id> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> + static member inline ``<*>`` (KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), _output: Id>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) + static member inline ``<*>`` (struct (a: 'Monoid, f), struct (b: 'Monoid, x: 'T), _output: Id, []_mthd: Apply) = struct (Plus.Invoke a b, f x) + + static member ``<*>`` (f: Map<'Key,_> , x: Map<'Key,'T> , _output: Id> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { for KeyValue(k, vf) in f do match Map.tryFind k x with | Some vx -> yield k, vf vx | _ -> () }) - static member ``<*>`` (f: Dictionary<'Key,_>, x: Dictionary<'Key,'T> , _output: Option> , []_mthd: Apply) : Dictionary<'Key,'U> = + static member ``<*>`` (f: Dictionary<'Key,_>, x: Dictionary<'Key,'T> , _output: Id> , []_mthd: Apply) : Dictionary<'Key,'U> = let dct = Dictionary () for KeyValue(k, vf) in f do match x.TryGetValue k with @@ -174,23 +174,23 @@ type Apply = dct #if !FABLE_COMPILER - static member ``<*>`` (f: Expr<'T->'U>, x: Expr<'T>, _output: Option>, []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) + static member ``<*>`` (f: Expr<'T->'U>, x: Expr<'T>, _output: Id>, []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) #endif - static member ``<*>`` (f: ('T->'U) ResizeArray, x: 'T ResizeArray, _output: Option<'U ResizeArray>, []_mthd: Apply) = + static member ``<*>`` (f: ('T->'U) ResizeArray, x: 'T ResizeArray, _output: Id<'U ResizeArray>, []_mthd: Apply) = ResizeArray (Seq.collect (fun x1 -> Seq.collect (fun x2 -> Seq.singleton (x1 x2)) x) f) : 'U ResizeArray static member inline Invoke (f: '``Applicative<'T -> 'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = - ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_ -> _) input1, input2, Some output, mthd) - call(Unchecked.defaultof, f, x, Unchecked.defaultof<'``Applicative<'U>``>) + ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_ -> _) input1, input2, output, mthd) + call(Unchecked.defaultof, f, x, Unchecked.defaultof``>>) static member inline InvokeOnInstance (f: '``Applicative<'T->'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) (f, x)) type Apply with - static member inline ``<*>`` (f: '``Monad<'T->'U>`` , x: '``Monad<'T>`` , _output: Option<'``Monad<'U>``> , _mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) - static member inline ``<*>`` (_: ^t when ^t : null and ^t: struct, _: ^u when ^u : null and ^u: struct, _output: Option< ^r> when ^r : null and ^r: struct, _mthd: Default1) = id - static member inline ``<*>`` (f: '``Applicative<'T->'U>``, x: '``Applicative<'T>`` , _output: Option<'``Applicative<'U>`` > , _mthd:Default1) : '``Applicative<'U>`` = Apply.InvokeOnInstance f x + static member inline ``<*>`` (f: '``Monad<'T->'U>`` , x: '``Monad<'T>`` , _output: Id<'``Monad<'U>``> , _mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) + static member inline ``<*>`` (_: ^t when ^t : null and ^t: struct, _: ^u when ^u : null and ^u: struct, _output: Id< ^r> when ^r : null and ^r: struct, _mthd: Default1) = id + static member inline ``<*>`` (f: '``Applicative<'T->'U>``, x: '``Applicative<'T>``, _output: Id<'``Applicative<'U>`` > , _mthd:Default1) : '``Applicative<'U>`` = Apply.InvokeOnInstance f x // Functor class ---------------------------------------------------------- From cdedad2c5b6848f254a91927c30d1b2f20094222 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sun, 8 Dec 2019 16:28:03 +0100 Subject: [PATCH 06/23] Revert "Use Id" This reverts commit cb2f49fb076278d4d0d9614d0f49492a0e569865. --- src/FSharpPlus/Functor.fs | 48 +++++++++++++++++++-------------------- 1 file changed, 24 insertions(+), 24 deletions(-) diff --git a/src/FSharpPlus/Functor.fs b/src/FSharpPlus/Functor.fs index a8fb7b7bc..4bd9b51d4 100644 --- a/src/FSharpPlus/Functor.fs +++ b/src/FSharpPlus/Functor.fs @@ -140,32 +140,32 @@ type Return = type Apply = inherit Default1 - static member ``<*>`` (f: Lazy<'T->'U> , x: Lazy<'T> , _output: Id> , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> - static member ``<*>`` (f: seq<_> , x: seq<'T> , _output: Id> , []_mthd: Apply) = Seq.apply f x : seq<'U> + static member ``<*>`` (f: Lazy<'T->'U> , x: Lazy<'T> , _output: Option> , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> + static member ``<*>`` (f: seq<_> , x: seq<'T> , _output: Option> , []_mthd: Apply) = Seq.apply f x : seq<'U> #if !FABLE_COMPILER - static member ``<*>`` (f: IEnumerator<_> , x: IEnumerator<'T> , _output: Id> , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> + static member ``<*>`` (f: IEnumerator<_> , x: IEnumerator<'T> , _output: Option> , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> #endif - static member ``<*>`` (f: list<_> , x: list<'T> , _output: Id> , []_mthd: Apply) = List.apply f x : list<'U> - static member ``<*>`` (f: _ [] , x: 'T [] , _output: Id<'U []> , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] - static member ``<*>`` (f: 'r -> _ , g: _ -> 'T , _output: Id< 'r -> 'U> , []_mthd: Apply) = fun x -> f x (g x) : 'U - static member inline ``<*>`` ((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , _output: Id<'Monoid * 'U> , []_mthd: Apply) = (FSharpPlus.Control.Plus.Invoke a b, f x) : 'Monoid *'U + static member ``<*>`` (f: list<_> , x: list<'T> , _output: Option> , []_mthd: Apply) = List.apply f x : list<'U> + static member ``<*>`` (f: _ [] , x: 'T [] , _output: Option<'U []> , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] + static member ``<*>`` (f: 'r -> _ , g: _ -> 'T , _output: Option< 'r -> 'U> , []_mthd: Apply) = fun x -> f x (g x) : 'U + static member inline ``<*>`` ((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , _output: Option<'Monoid * 'U> , []_mthd: Apply) = (FSharpPlus.Control.Plus.Invoke a b, f x) : 'Monoid *'U #if !FABLE_COMPILER - static member ``<*>`` (f: Task<_> , x: Task<'T> , _output: Id> , []_mthd: Apply) = Task.apply f x : Task<'U> + static member ``<*>`` (f: Task<_> , x: Task<'T> , _output: Option> , []_mthd: Apply) = Task.apply f x : Task<'U> #endif - static member ``<*>`` (f: Async<_> , x: Async<'T> , _output: Id> , []_mthd: Apply) = Async.apply f x : Async<'U> - static member ``<*>`` (f: option<_> , x: option<'T> , _output: Id> , []_mthd: Apply) = Option.apply f x : option<'U> - static member ``<*>`` (f: Result<_,'E> , x: Result<'T,'E> , _output: Id> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> - static member ``<*>`` (f: Choice<_,'E> , x: Choice<'T,'E> , _output: Id> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> - static member inline ``<*>`` (KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), _output: Id>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) - static member inline ``<*>`` (struct (a: 'Monoid, f), struct (b: 'Monoid, x: 'T), _output: Id, []_mthd: Apply) = struct (Plus.Invoke a b, f x) - - static member ``<*>`` (f: Map<'Key,_> , x: Map<'Key,'T> , _output: Id> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { + static member ``<*>`` (f: Async<_> , x: Async<'T> , _output: Option> , []_mthd: Apply) = Async.apply f x : Async<'U> + static member ``<*>`` (f: option<_> , x: option<'T> , _output: Option> , []_mthd: Apply) = Option.apply f x : option<'U> + static member ``<*>`` (f: Result<_,'E> , x: Result<'T,'E> , _output: Option> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> + static member ``<*>`` (f: Choice<_,'E> , x: Choice<'T,'E> , _output: Option> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> + static member inline ``<*>`` (KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), _output: Option>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (FSharpPlus.Control.Plus.Invoke a b, f x) + static member inline ``<*>`` (struct (a: 'Monoid, f), struct (b: 'Monoid, x: 'T), _output: Option, []_mthd: Apply) = struct (FSharpPlus.Control.Plus.Invoke a b, f x) + + static member ``<*>`` (f: Map<'Key,_> , x: Map<'Key,'T> , _output: Option> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { for KeyValue(k, vf) in f do match Map.tryFind k x with | Some vx -> yield k, vf vx | _ -> () }) - static member ``<*>`` (f: Dictionary<'Key,_>, x: Dictionary<'Key,'T> , _output: Id> , []_mthd: Apply) : Dictionary<'Key,'U> = + static member ``<*>`` (f: Dictionary<'Key,_>, x: Dictionary<'Key,'T> , _output: Option> , []_mthd: Apply) : Dictionary<'Key,'U> = let dct = Dictionary () for KeyValue(k, vf) in f do match x.TryGetValue k with @@ -174,23 +174,23 @@ type Apply = dct #if !FABLE_COMPILER - static member ``<*>`` (f: Expr<'T->'U>, x: Expr<'T>, _output: Id>, []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) + static member ``<*>`` (f: Expr<'T->'U>, x: Expr<'T>, _output: Option>, []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) #endif - static member ``<*>`` (f: ('T->'U) ResizeArray, x: 'T ResizeArray, _output: Id<'U ResizeArray>, []_mthd: Apply) = + static member ``<*>`` (f: ('T->'U) ResizeArray, x: 'T ResizeArray, _output: Option<'U ResizeArray>, []_mthd: Apply) = ResizeArray (Seq.collect (fun x1 -> Seq.collect (fun x2 -> Seq.singleton (x1 x2)) x) f) : 'U ResizeArray static member inline Invoke (f: '``Applicative<'T -> 'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = - ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_ -> _) input1, input2, output, mthd) - call(Unchecked.defaultof, f, x, Unchecked.defaultof``>>) + ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_ -> _) input1, input2, Some output, mthd) + call(Unchecked.defaultof, f, x, Unchecked.defaultof<'``Applicative<'U>``>) static member inline InvokeOnInstance (f: '``Applicative<'T->'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) (f, x)) type Apply with - static member inline ``<*>`` (f: '``Monad<'T->'U>`` , x: '``Monad<'T>`` , _output: Id<'``Monad<'U>``> , _mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) - static member inline ``<*>`` (_: ^t when ^t : null and ^t: struct, _: ^u when ^u : null and ^u: struct, _output: Id< ^r> when ^r : null and ^r: struct, _mthd: Default1) = id - static member inline ``<*>`` (f: '``Applicative<'T->'U>``, x: '``Applicative<'T>``, _output: Id<'``Applicative<'U>`` > , _mthd:Default1) : '``Applicative<'U>`` = Apply.InvokeOnInstance f x + static member inline ``<*>`` (f: '``Monad<'T->'U>`` , x: '``Monad<'T>`` , _output: Option<'``Monad<'U>``> , _mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) + static member inline ``<*>`` (_: ^t when ^t : null and ^t: struct, _: ^u when ^u : null and ^u: struct, _output: Option< ^r> when ^r : null and ^r: struct, _mthd: Default1) = id + static member inline ``<*>`` (f: '``Applicative<'T->'U>``, x: '``Applicative<'T>`` , _output: Option<'``Applicative<'U>`` > , _mthd:Default1) : '``Applicative<'U>`` = Apply.InvokeOnInstance f x // Functor class ---------------------------------------------------------- From 14d6f32381de2c0fb737e1b88291adbd985a4d74 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sun, 8 Dec 2019 16:37:36 +0100 Subject: [PATCH 07/23] Revert 0177fb6d3879d7956b4f75c01f7b808c97c71c86 --- src/FSharpPlus/Functor.fs | 1 - 1 file changed, 1 deletion(-) diff --git a/src/FSharpPlus/Functor.fs b/src/FSharpPlus/Functor.fs index 4bd9b51d4..ac80072f7 100644 --- a/src/FSharpPlus/Functor.fs +++ b/src/FSharpPlus/Functor.fs @@ -157,7 +157,6 @@ type Apply = static member ``<*>`` (f: Result<_,'E> , x: Result<'T,'E> , _output: Option> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> static member ``<*>`` (f: Choice<_,'E> , x: Choice<'T,'E> , _output: Option> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> static member inline ``<*>`` (KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), _output: Option>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (FSharpPlus.Control.Plus.Invoke a b, f x) - static member inline ``<*>`` (struct (a: 'Monoid, f), struct (b: 'Monoid, x: 'T), _output: Option, []_mthd: Apply) = struct (FSharpPlus.Control.Plus.Invoke a b, f x) static member ``<*>`` (f: Map<'Key,_> , x: Map<'Key,'T> , _output: Option> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { for KeyValue(k, vf) in f do From 1c000069608d858be9b0de82d8dd138993874b7b Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sun, 8 Dec 2019 19:32:35 +0100 Subject: [PATCH 08/23] Re-organize code --- src/FSharpPlus/Functor.fs | 13 ++++++------- 1 file changed, 6 insertions(+), 7 deletions(-) diff --git a/src/FSharpPlus/Functor.fs b/src/FSharpPlus/Functor.fs index ac80072f7..d84fa2079 100644 --- a/src/FSharpPlus/Functor.fs +++ b/src/FSharpPlus/Functor.fs @@ -148,7 +148,7 @@ type Apply = static member ``<*>`` (f: list<_> , x: list<'T> , _output: Option> , []_mthd: Apply) = List.apply f x : list<'U> static member ``<*>`` (f: _ [] , x: 'T [] , _output: Option<'U []> , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] static member ``<*>`` (f: 'r -> _ , g: _ -> 'T , _output: Option< 'r -> 'U> , []_mthd: Apply) = fun x -> f x (g x) : 'U - static member inline ``<*>`` ((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , _output: Option<'Monoid * 'U> , []_mthd: Apply) = (FSharpPlus.Control.Plus.Invoke a b, f x) : 'Monoid *'U + static member inline ``<*>`` ((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , _output: Option<'Monoid * 'U> , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U #if !FABLE_COMPILER static member ``<*>`` (f: Task<_> , x: Task<'T> , _output: Option> , []_mthd: Apply) = Task.apply f x : Task<'U> #endif @@ -156,7 +156,7 @@ type Apply = static member ``<*>`` (f: option<_> , x: option<'T> , _output: Option> , []_mthd: Apply) = Option.apply f x : option<'U> static member ``<*>`` (f: Result<_,'E> , x: Result<'T,'E> , _output: Option> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> static member ``<*>`` (f: Choice<_,'E> , x: Choice<'T,'E> , _output: Option> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> - static member inline ``<*>`` (KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), _output: Option>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (FSharpPlus.Control.Plus.Invoke a b, f x) + static member inline ``<*>`` (KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), _output: Option>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) static member ``<*>`` (f: Map<'Key,_> , x: Map<'Key,'T> , _output: Option> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { for KeyValue(k, vf) in f do @@ -179,17 +179,16 @@ type Apply = ResizeArray (Seq.collect (fun x1 -> Seq.collect (fun x2 -> Seq.singleton (x1 x2)) x) f) : 'U ResizeArray static member inline Invoke (f: '``Applicative<'T -> 'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = - let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = - ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_ -> _) input1, input2, Some output, mthd) - call(Unchecked.defaultof, f, x, Unchecked.defaultof<'``Applicative<'U>``>) + let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_ -> _) input1, input2, output, mthd) + call(Unchecked.defaultof, f, x, Unchecked.defaultof``>>) static member inline InvokeOnInstance (f: '``Applicative<'T->'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) (f, x)) type Apply with - static member inline ``<*>`` (f: '``Monad<'T->'U>`` , x: '``Monad<'T>`` , _output: Option<'``Monad<'U>``> , _mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) + static member inline ``<*>`` (f: '``Monad<'T->'U>`` , x: '``Monad<'T>`` , _output: Option<'``Monad<'U>``> , _mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) + static member inline ``<*>`` (f: '``Applicative<'T->'U>``, x: '``Applicative<'T>``, _output: Option<'``Applicative<'U>``>, _mthd:Default1) : '``Applicative<'U>`` = Apply.InvokeOnInstance f x static member inline ``<*>`` (_: ^t when ^t : null and ^t: struct, _: ^u when ^u : null and ^u: struct, _output: Option< ^r> when ^r : null and ^r: struct, _mthd: Default1) = id - static member inline ``<*>`` (f: '``Applicative<'T->'U>``, x: '``Applicative<'T>`` , _output: Option<'``Applicative<'U>`` > , _mthd:Default1) : '``Applicative<'U>`` = Apply.InvokeOnInstance f x // Functor class ---------------------------------------------------------- From ab857c97abebee966dcf3b028fa3cb697b9e562c Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sun, 8 Dec 2019 19:48:04 +0100 Subject: [PATCH 09/23] Fix - create the option later --- src/FSharpPlus/Functor.fs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/FSharpPlus/Functor.fs b/src/FSharpPlus/Functor.fs index d84fa2079..01ee9a138 100644 --- a/src/FSharpPlus/Functor.fs +++ b/src/FSharpPlus/Functor.fs @@ -179,8 +179,8 @@ type Apply = ResizeArray (Seq.collect (fun x1 -> Seq.collect (fun x2 -> Seq.singleton (x1 x2)) x) f) : 'U ResizeArray static member inline Invoke (f: '``Applicative<'T -> 'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = - let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_ -> _) input1, input2, output, mthd) - call(Unchecked.defaultof, f, x, Unchecked.defaultof``>>) + let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_ -> _) input1, input2, Some output, mthd) + call(Unchecked.defaultof, f, x, Unchecked.defaultof<'``Applicative<'U>``>) static member inline InvokeOnInstance (f: '``Applicative<'T->'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) (f, x)) From 0371165809bfa1c4213c43630775fd14ea6aa473 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sun, 8 Dec 2019 20:26:11 +0100 Subject: [PATCH 10/23] Use ref instead of option --- src/FSharpPlus/Functor.fs | 42 +++++++++++++++++++-------------------- 1 file changed, 21 insertions(+), 21 deletions(-) diff --git a/src/FSharpPlus/Functor.fs b/src/FSharpPlus/Functor.fs index 01ee9a138..bb33eab11 100644 --- a/src/FSharpPlus/Functor.fs +++ b/src/FSharpPlus/Functor.fs @@ -140,31 +140,31 @@ type Return = type Apply = inherit Default1 - static member ``<*>`` (f: Lazy<'T->'U> , x: Lazy<'T> , _output: Option> , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> - static member ``<*>`` (f: seq<_> , x: seq<'T> , _output: Option> , []_mthd: Apply) = Seq.apply f x : seq<'U> + static member ``<*>`` (f: Lazy<'T->'U> , x: Lazy<'T> , _output: ref> , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> + static member ``<*>`` (f: seq<_> , x: seq<'T> , _output: ref> , []_mthd: Apply) = Seq.apply f x : seq<'U> #if !FABLE_COMPILER - static member ``<*>`` (f: IEnumerator<_> , x: IEnumerator<'T> , _output: Option> , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> + static member ``<*>`` (f: IEnumerator<_> , x: IEnumerator<'T> , _output: ref> , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> #endif - static member ``<*>`` (f: list<_> , x: list<'T> , _output: Option> , []_mthd: Apply) = List.apply f x : list<'U> - static member ``<*>`` (f: _ [] , x: 'T [] , _output: Option<'U []> , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] - static member ``<*>`` (f: 'r -> _ , g: _ -> 'T , _output: Option< 'r -> 'U> , []_mthd: Apply) = fun x -> f x (g x) : 'U - static member inline ``<*>`` ((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , _output: Option<'Monoid * 'U> , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U + static member ``<*>`` (f: list<_> , x: list<'T> , _output: ref> , []_mthd: Apply) = List.apply f x : list<'U> + static member ``<*>`` (f: _ [] , x: 'T [] , _output: ref<'U []> , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] + static member ``<*>`` (f: 'r -> _ , g: _ -> 'T , _output: ref< 'r -> 'U> , []_mthd: Apply) = fun x -> f x (g x) : 'U + static member inline ``<*>`` ((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , _output: ref<'Monoid * 'U> , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U #if !FABLE_COMPILER - static member ``<*>`` (f: Task<_> , x: Task<'T> , _output: Option> , []_mthd: Apply) = Task.apply f x : Task<'U> + static member ``<*>`` (f: Task<_> , x: Task<'T> , _output: ref> , []_mthd: Apply) = Task.apply f x : Task<'U> #endif - static member ``<*>`` (f: Async<_> , x: Async<'T> , _output: Option> , []_mthd: Apply) = Async.apply f x : Async<'U> - static member ``<*>`` (f: option<_> , x: option<'T> , _output: Option> , []_mthd: Apply) = Option.apply f x : option<'U> - static member ``<*>`` (f: Result<_,'E> , x: Result<'T,'E> , _output: Option> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> - static member ``<*>`` (f: Choice<_,'E> , x: Choice<'T,'E> , _output: Option> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> - static member inline ``<*>`` (KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), _output: Option>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) + static member ``<*>`` (f: Async<_> , x: Async<'T> , _output: ref> , []_mthd: Apply) = Async.apply f x : Async<'U> + static member ``<*>`` (f: option<_> , x: option<'T> , _output: ref> , []_mthd: Apply) = Option.apply f x : option<'U> + static member ``<*>`` (f: Result<_,'E> , x: Result<'T,'E> , _output: ref> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> + static member ``<*>`` (f: Choice<_,'E> , x: Choice<'T,'E> , _output: ref> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> + static member inline ``<*>`` (KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), _output: ref>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) - static member ``<*>`` (f: Map<'Key,_> , x: Map<'Key,'T> , _output: Option> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { + static member ``<*>`` (f: Map<'Key,_> , x: Map<'Key,'T> , _output: ref> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { for KeyValue(k, vf) in f do match Map.tryFind k x with | Some vx -> yield k, vf vx | _ -> () }) - static member ``<*>`` (f: Dictionary<'Key,_>, x: Dictionary<'Key,'T> , _output: Option> , []_mthd: Apply) : Dictionary<'Key,'U> = + static member ``<*>`` (f: Dictionary<'Key,_>, x: Dictionary<'Key,'T> , _output: ref> , []_mthd: Apply) : Dictionary<'Key,'U> = let dct = Dictionary () for KeyValue(k, vf) in f do match x.TryGetValue k with @@ -173,22 +173,22 @@ type Apply = dct #if !FABLE_COMPILER - static member ``<*>`` (f: Expr<'T->'U>, x: Expr<'T>, _output: Option>, []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) + static member ``<*>`` (f: Expr<'T->'U>, x: Expr<'T>, _output: ref>, []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) #endif - static member ``<*>`` (f: ('T->'U) ResizeArray, x: 'T ResizeArray, _output: Option<'U ResizeArray>, []_mthd: Apply) = + static member ``<*>`` (f: ('T->'U) ResizeArray, x: 'T ResizeArray, _output: ref<'U ResizeArray>, []_mthd: Apply) = ResizeArray (Seq.collect (fun x1 -> Seq.collect (fun x2 -> Seq.singleton (x1 x2)) x) f) : 'U ResizeArray static member inline Invoke (f: '``Applicative<'T -> 'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = - let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_ -> _) input1, input2, Some output, mthd) + let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_ -> _) input1, input2, ref output, mthd) call(Unchecked.defaultof, f, x, Unchecked.defaultof<'``Applicative<'U>``>) static member inline InvokeOnInstance (f: '``Applicative<'T->'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) (f, x)) type Apply with - static member inline ``<*>`` (f: '``Monad<'T->'U>`` , x: '``Monad<'T>`` , _output: Option<'``Monad<'U>``> , _mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) - static member inline ``<*>`` (f: '``Applicative<'T->'U>``, x: '``Applicative<'T>``, _output: Option<'``Applicative<'U>``>, _mthd:Default1) : '``Applicative<'U>`` = Apply.InvokeOnInstance f x - static member inline ``<*>`` (_: ^t when ^t : null and ^t: struct, _: ^u when ^u : null and ^u: struct, _output: Option< ^r> when ^r : null and ^r: struct, _mthd: Default1) = id + static member inline ``<*>`` (f: '``Monad<'T->'U>`` , x: '``Monad<'T>`` , _output: ref<'``Monad<'U>``> , _mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) + static member inline ``<*>`` (f: '``Applicative<'T->'U>``, x: '``Applicative<'T>``, _output: ref<'``Applicative<'U>``>, _mthd:Default1) : '``Applicative<'U>`` = Apply.InvokeOnInstance f x + static member inline ``<*>`` (_: ^t when ^t : null and ^t: struct, _: ^u when ^u : null and ^u: struct, _output: ref< ^r> when ^r : null and ^r: struct, _mthd: Default1) = id // Functor class ---------------------------------------------------------- From 88dcec8c31a7d957fdc1402e0e0ff841d0dd9494 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sun, 8 Dec 2019 23:13:36 +0100 Subject: [PATCH 11/23] Add test --- tests/FSharpPlus.Tests/General.fs | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/tests/FSharpPlus.Tests/General.fs b/tests/FSharpPlus.Tests/General.fs index 7fe87e184..81e412d66 100644 --- a/tests/FSharpPlus.Tests/General.fs +++ b/tests/FSharpPlus.Tests/General.fs @@ -1018,6 +1018,10 @@ module Applicative = Assert.AreEqual (606, res606) Assert.AreEqual (508, res508) Assert.AreEqual (toList (run res9n5), toList (run' res9n5')) + + // WrappedSeqC is Monad. Monads are Applicatives => (<*>) should work + let (res2: WrappedSeqC<_>) = WrappedSeqC [(+) 1] <*> WrappedSeqC [2] + Assert.AreEqual (WrappedSeqC [3], res2) // Idiom brackets from http://www.haskell.org/haskellwiki/Idiom_brackets From fc74a9134695e63947f96b36b127fc11cce7b167 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Mon, 9 Dec 2019 07:19:40 +0100 Subject: [PATCH 12/23] Use structural equality check --- tests/FSharpPlus.Tests/General.fs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/FSharpPlus.Tests/General.fs b/tests/FSharpPlus.Tests/General.fs index 81e412d66..cd58b4fbd 100644 --- a/tests/FSharpPlus.Tests/General.fs +++ b/tests/FSharpPlus.Tests/General.fs @@ -1021,7 +1021,7 @@ module Applicative = // WrappedSeqC is Monad. Monads are Applicatives => (<*>) should work let (res2: WrappedSeqC<_>) = WrappedSeqC [(+) 1] <*> WrappedSeqC [2] - Assert.AreEqual (WrappedSeqC [3], res2) + Assert.True (WrappedSeqC [3] = res2) // Idiom brackets from http://www.haskell.org/haskellwiki/Idiom_brackets From 5636a8f6eed424d5b5ad8eb684bf00f0dce8c3b2 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Mon, 9 Dec 2019 07:57:13 +0100 Subject: [PATCH 13/23] Use CollectionAssert.AreEqual --- tests/FSharpPlus.Tests/General.fs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/FSharpPlus.Tests/General.fs b/tests/FSharpPlus.Tests/General.fs index cd58b4fbd..c7cd03115 100644 --- a/tests/FSharpPlus.Tests/General.fs +++ b/tests/FSharpPlus.Tests/General.fs @@ -1021,7 +1021,7 @@ module Applicative = // WrappedSeqC is Monad. Monads are Applicatives => (<*>) should work let (res2: WrappedSeqC<_>) = WrappedSeqC [(+) 1] <*> WrappedSeqC [2] - Assert.True (WrappedSeqC [3] = res2) + CollectionAssert.AreEqual (WrappedSeqC [3], res2) // Idiom brackets from http://www.haskell.org/haskellwiki/Idiom_brackets From fea4b08e8ddb8ddce36da264a6b53d07b8fe4d8d Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Mon, 9 Dec 2019 08:42:38 +0100 Subject: [PATCH 14/23] Restore Optional attribute --- src/FSharpPlus/Functor.fs | 34 +++++++++++++++++----------------- 1 file changed, 17 insertions(+), 17 deletions(-) diff --git a/src/FSharpPlus/Functor.fs b/src/FSharpPlus/Functor.fs index bb33eab11..10778b493 100644 --- a/src/FSharpPlus/Functor.fs +++ b/src/FSharpPlus/Functor.fs @@ -140,31 +140,31 @@ type Return = type Apply = inherit Default1 - static member ``<*>`` (f: Lazy<'T->'U> , x: Lazy<'T> , _output: ref> , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> - static member ``<*>`` (f: seq<_> , x: seq<'T> , _output: ref> , []_mthd: Apply) = Seq.apply f x : seq<'U> + static member ``<*>`` (f: Lazy<'T->'U> , x: Lazy<'T> , []_output: ref> , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> + static member ``<*>`` (f: seq<_> , x: seq<'T> , []_output: ref> , []_mthd: Apply) = Seq.apply f x : seq<'U> #if !FABLE_COMPILER - static member ``<*>`` (f: IEnumerator<_> , x: IEnumerator<'T> , _output: ref> , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> + static member ``<*>`` (f: IEnumerator<_> , x: IEnumerator<'T> , []_output: ref> , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> #endif - static member ``<*>`` (f: list<_> , x: list<'T> , _output: ref> , []_mthd: Apply) = List.apply f x : list<'U> - static member ``<*>`` (f: _ [] , x: 'T [] , _output: ref<'U []> , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] - static member ``<*>`` (f: 'r -> _ , g: _ -> 'T , _output: ref< 'r -> 'U> , []_mthd: Apply) = fun x -> f x (g x) : 'U - static member inline ``<*>`` ((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , _output: ref<'Monoid * 'U> , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U + static member ``<*>`` (f: list<_> , x: list<'T> , []_output: ref> , []_mthd: Apply) = List.apply f x : list<'U> + static member ``<*>`` (f: _ [] , x: 'T [] , []_output: ref<'U []> , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] + static member ``<*>`` (f: 'r -> _ , g: _ -> 'T , []_output: ref< 'r -> 'U> , []_mthd: Apply) = fun x -> f x (g x) : 'U + static member inline ``<*>`` ((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , []_output: ref<'Monoid * 'U> , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U #if !FABLE_COMPILER - static member ``<*>`` (f: Task<_> , x: Task<'T> , _output: ref> , []_mthd: Apply) = Task.apply f x : Task<'U> + static member ``<*>`` (f: Task<_> , x: Task<'T> , []_output: ref> , []_mthd: Apply) = Task.apply f x : Task<'U> #endif - static member ``<*>`` (f: Async<_> , x: Async<'T> , _output: ref> , []_mthd: Apply) = Async.apply f x : Async<'U> - static member ``<*>`` (f: option<_> , x: option<'T> , _output: ref> , []_mthd: Apply) = Option.apply f x : option<'U> - static member ``<*>`` (f: Result<_,'E> , x: Result<'T,'E> , _output: ref> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> - static member ``<*>`` (f: Choice<_,'E> , x: Choice<'T,'E> , _output: ref> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> - static member inline ``<*>`` (KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), _output: ref>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) + static member ``<*>`` (f: Async<_> , x: Async<'T> , []_output: ref> , []_mthd: Apply) = Async.apply f x : Async<'U> + static member ``<*>`` (f: option<_> , x: option<'T> , []_output: ref> , []_mthd: Apply) = Option.apply f x : option<'U> + static member ``<*>`` (f: Result<_,'E> , x: Result<'T,'E> , []_output: ref> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> + static member ``<*>`` (f: Choice<_,'E> , x: Choice<'T,'E> , []_output: ref> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> + static member inline ``<*>`` (KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), []_output: ref>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) - static member ``<*>`` (f: Map<'Key,_> , x: Map<'Key,'T> , _output: ref> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { + static member ``<*>`` (f: Map<'Key,_> , x: Map<'Key,'T> , []_output: ref> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { for KeyValue(k, vf) in f do match Map.tryFind k x with | Some vx -> yield k, vf vx | _ -> () }) - static member ``<*>`` (f: Dictionary<'Key,_>, x: Dictionary<'Key,'T> , _output: ref> , []_mthd: Apply) : Dictionary<'Key,'U> = + static member ``<*>`` (f: Dictionary<'Key,_>, x: Dictionary<'Key,'T> , []_output: ref> , []_mthd: Apply) : Dictionary<'Key,'U> = let dct = Dictionary () for KeyValue(k, vf) in f do match x.TryGetValue k with @@ -173,9 +173,9 @@ type Apply = dct #if !FABLE_COMPILER - static member ``<*>`` (f: Expr<'T->'U>, x: Expr<'T>, _output: ref>, []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) + static member ``<*>`` (f: Expr<'T->'U>, x: Expr<'T>, []_output: ref>, []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) #endif - static member ``<*>`` (f: ('T->'U) ResizeArray, x: 'T ResizeArray, _output: ref<'U ResizeArray>, []_mthd: Apply) = + static member ``<*>`` (f: ('T->'U) ResizeArray, x: 'T ResizeArray, []_output: ref<'U ResizeArray>, []_mthd: Apply) = ResizeArray (Seq.collect (fun x1 -> Seq.collect (fun x2 -> Seq.singleton (x1 x2)) x) f) : 'U ResizeArray static member inline Invoke (f: '``Applicative<'T -> 'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = From 7d42e8b2ca31a83450007475fde6060f5e3ede04 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Mon, 9 Dec 2019 08:46:11 +0100 Subject: [PATCH 15/23] Minimize diff --- src/FSharpPlus/Functor.fs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/FSharpPlus/Functor.fs b/src/FSharpPlus/Functor.fs index 10778b493..b79942872 100644 --- a/src/FSharpPlus/Functor.fs +++ b/src/FSharpPlus/Functor.fs @@ -179,7 +179,8 @@ type Apply = ResizeArray (Seq.collect (fun x1 -> Seq.collect (fun x2 -> Seq.singleton (x1 x2)) x) f) : 'U ResizeArray static member inline Invoke (f: '``Applicative<'T -> 'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = - let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_ -> _) input1, input2, ref output, mthd) + let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = + ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_ -> _) input1, input2, ref output, mthd) call(Unchecked.defaultof, f, x, Unchecked.defaultof<'``Applicative<'U>``>) static member inline InvokeOnInstance (f: '``Applicative<'T->'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = From 3537edcf308b8db3aaad0253e333a9479add1359 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Tue, 10 Dec 2019 08:53:41 +0100 Subject: [PATCH 16/23] Wrap a duplicate input parameter --- src/FSharpPlus/Functor.fs | 42 +++++++++++++++++++-------------------- 1 file changed, 21 insertions(+), 21 deletions(-) diff --git a/src/FSharpPlus/Functor.fs b/src/FSharpPlus/Functor.fs index b79942872..34173b240 100644 --- a/src/FSharpPlus/Functor.fs +++ b/src/FSharpPlus/Functor.fs @@ -140,31 +140,31 @@ type Return = type Apply = inherit Default1 - static member ``<*>`` (f: Lazy<'T->'U> , x: Lazy<'T> , []_output: ref> , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> - static member ``<*>`` (f: seq<_> , x: seq<'T> , []_output: ref> , []_mthd: Apply) = Seq.apply f x : seq<'U> + static member ``<*>`` (f: Lazy<'T->'U> , _: ref'U>> , x: Lazy<'T> , []_output: Lazy<'U> , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> + static member ``<*>`` (f: seq<_> , _: ref> , x: seq<'T> , []_output: seq<'U> , []_mthd: Apply) = Seq.apply f x : seq<'U> #if !FABLE_COMPILER - static member ``<*>`` (f: IEnumerator<_> , x: IEnumerator<'T> , []_output: ref> , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> + static member ``<*>`` (f: IEnumerator<_> , _: ref>, x: IEnumerator<'T>, []_output: IEnumerator<'U> , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> #endif - static member ``<*>`` (f: list<_> , x: list<'T> , []_output: ref> , []_mthd: Apply) = List.apply f x : list<'U> - static member ``<*>`` (f: _ [] , x: 'T [] , []_output: ref<'U []> , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] - static member ``<*>`` (f: 'r -> _ , g: _ -> 'T , []_output: ref< 'r -> 'U> , []_mthd: Apply) = fun x -> f x (g x) : 'U - static member inline ``<*>`` ((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , []_output: ref<'Monoid * 'U> , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U + static member ``<*>`` (f: list<_> , _: ref> , x: list<'T> , []_output: list<'U> , []_mthd: Apply) = List.apply f x : list<'U> + static member ``<*>`` (f: _ [] , _: ref<_ []> , x: 'T [] , []_output: 'U [] , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] + static member ``<*>`` (f: 'r -> _ , _: ref<'r -> _> , g: _ -> 'T , []_output: 'r -> 'U , []_mthd: Apply) = fun x -> f x (g x) : 'U + static member inline ``<*>`` ((a: 'Monoid, f) , _: ref<'Monoid * _>, (b: 'Monoid, x: 'T) , []_output: 'Monoid * 'U , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U #if !FABLE_COMPILER - static member ``<*>`` (f: Task<_> , x: Task<'T> , []_output: ref> , []_mthd: Apply) = Task.apply f x : Task<'U> + static member ``<*>`` (f: Task<_> , _: ref> , x: Task<'T> , []_output: Task<'U> , []_mthd: Apply) = Task.apply f x : Task<'U> #endif - static member ``<*>`` (f: Async<_> , x: Async<'T> , []_output: ref> , []_mthd: Apply) = Async.apply f x : Async<'U> - static member ``<*>`` (f: option<_> , x: option<'T> , []_output: ref> , []_mthd: Apply) = Option.apply f x : option<'U> - static member ``<*>`` (f: Result<_,'E> , x: Result<'T,'E> , []_output: ref> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> - static member ``<*>`` (f: Choice<_,'E> , x: Choice<'T,'E> , []_output: ref> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> - static member inline ``<*>`` (KeyValue(a: 'Key, f), KeyValue(b: 'Key, x: 'T), []_output: ref>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) + static member ``<*>`` (f: Async<_> , _: ref> , x: Async<'T> , []_output: Async<'U> , []_mthd: Apply) = Async.apply f x : Async<'U> + static member ``<*>`` (f: option<_> , _: ref> , x: option<'T> , []_output: option<'U> , []_mthd: Apply) = Option.apply f x : option<'U> + static member ``<*>`` (f: Result<_,'E> , _: ref> , x: Result<'T,'E> , []_output: Result<'b,'E> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> + static member ``<*>`` (f: Choice<_,'E> , _: ref> , x: Choice<'T,'E> , []_output: Choice<'b,'E> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> + static member inline ``<*>`` (KeyValue(a: 'Key, f), _: ref>, KeyValue(b: 'Key, x: 'T), []_output: KeyValuePair<'Key,'U>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) - static member ``<*>`` (f: Map<'Key,_> , x: Map<'Key,'T> , []_output: ref> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { + static member ``<*>`` (f: Map<'Key,_> , _: ref>, x: Map<'Key,'T> , []_output: Map<'Key,'U> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { for KeyValue(k, vf) in f do match Map.tryFind k x with | Some vx -> yield k, vf vx | _ -> () }) - static member ``<*>`` (f: Dictionary<'Key,_>, x: Dictionary<'Key,'T> , []_output: ref> , []_mthd: Apply) : Dictionary<'Key,'U> = + static member ``<*>`` (f: Dictionary<'Key,_>, _: ref>, x: Dictionary<'Key,'T> , []_output: Dictionary<'Key,'U> , []_mthd: Apply) : Dictionary<'Key,'U> = let dct = Dictionary () for KeyValue(k, vf) in f do match x.TryGetValue k with @@ -173,23 +173,23 @@ type Apply = dct #if !FABLE_COMPILER - static member ``<*>`` (f: Expr<'T->'U>, x: Expr<'T>, []_output: ref>, []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) + static member ``<*>`` (f: Expr<'T->'U>, _: ref'U>>, x: Expr<'T>, []_output: Expr<'U>, []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) #endif - static member ``<*>`` (f: ('T->'U) ResizeArray, x: 'T ResizeArray, []_output: ref<'U ResizeArray>, []_mthd: Apply) = + static member ``<*>`` (f: ('T->'U) ResizeArray, _: ref<('T->'U) ResizeArray>, x: 'T ResizeArray, []_output: 'U ResizeArray, []_mthd: Apply) = ResizeArray (Seq.collect (fun x1 -> Seq.collect (fun x2 -> Seq.singleton (x1 x2)) x) f) : 'U ResizeArray static member inline Invoke (f: '``Applicative<'T -> 'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = - ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_ -> _) input1, input2, ref output, mthd) + ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_*_ -> _) input1, ref input1, input2, output, mthd) call(Unchecked.defaultof, f, x, Unchecked.defaultof<'``Applicative<'U>``>) static member inline InvokeOnInstance (f: '``Applicative<'T->'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) (f, x)) type Apply with - static member inline ``<*>`` (f: '``Monad<'T->'U>`` , x: '``Monad<'T>`` , _output: ref<'``Monad<'U>``> , _mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) - static member inline ``<*>`` (f: '``Applicative<'T->'U>``, x: '``Applicative<'T>``, _output: ref<'``Applicative<'U>``>, _mthd:Default1) : '``Applicative<'U>`` = Apply.InvokeOnInstance f x - static member inline ``<*>`` (_: ^t when ^t : null and ^t: struct, _: ^u when ^u : null and ^u: struct, _output: ref< ^r> when ^r : null and ^r: struct, _mthd: Default1) = id + static member inline ``<*>`` (f: '``Monad<'T->'U>`` , _: ref<'``Monad<'T->'U>``> , x: '``Monad<'T>`` , _output: '``Monad<'U>`` , _mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) + static member inline ``<*>`` (f: '``Applicative<'T->'U>``, _: ref<'``Applicative<'T->'U>``>, x: '``Applicative<'T>``, _output: '``Applicative<'U>``, _mthd:Default1) : '``Applicative<'U>`` = Apply.InvokeOnInstance f x + static member inline ``<*>`` (_: ^t when ^t : null and ^t: struct, _, _: ^u when ^u : null and ^u: struct, _output: ^r when ^r : null and ^r: struct, _mthd: Default1) = id // Functor class ---------------------------------------------------------- From 2b9416b9ee01173db1d8cfbc67c706ec396deffe Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Tue, 10 Dec 2019 09:15:22 +0100 Subject: [PATCH 17/23] Add test for user defined types --- tests/FSharpPlus.Tests/General.fs | 17 ++++++++++++++--- 1 file changed, 14 insertions(+), 3 deletions(-) diff --git a/tests/FSharpPlus.Tests/General.fs b/tests/FSharpPlus.Tests/General.fs index c7cd03115..b6516e967 100644 --- a/tests/FSharpPlus.Tests/General.fs +++ b/tests/FSharpPlus.Tests/General.fs @@ -165,6 +165,14 @@ type WrappedSeqD<'s> = WrappedSeqD of 's seq with static member Return x = SideEffects.add "Using WrappedSeqD's Return"; WrappedSeqD (Seq.singleton x) static member (<*>) (WrappedSeqD f, WrappedSeqD x) = SideEffects.add "Using WrappedSeqD's Return"; WrappedSeqD (f <*> x) static member ToList (WrappedSeqD x) = Seq.toList x + +type WrappedSeqE<'s> = WrappedSeqE of 's seq with + interface Collections.Generic.IEnumerable<'s> with member x.GetEnumerator () = (let (WrappedSeqE x) = x in x).GetEnumerator () + interface Collections.IEnumerable with member x.GetEnumerator () = (let (WrappedSeqE x) = x in x).GetEnumerator () :> Collections.IEnumerator + static member Return x = SideEffects.add "Using WrappedSeqE's Return"; WrappedSeqE (Seq.singleton x) + static member (<*>) (WrappedSeqE f, WrappedSeqE x) = SideEffects.add "Using WrappedSeqE's Apply"; WrappedSeqE (f <*> x) + static member ToList (WrappedSeqE x) = Seq.toList x + open System.Collections.Generic open System.Collections @@ -1020,9 +1028,12 @@ module Applicative = Assert.AreEqual (toList (run res9n5), toList (run' res9n5')) // WrappedSeqC is Monad. Monads are Applicatives => (<*>) should work - let (res2: WrappedSeqC<_>) = WrappedSeqC [(+) 1] <*> WrappedSeqC [2] - CollectionAssert.AreEqual (WrappedSeqC [3], res2) - + let (res3: WrappedSeqC<_>) = WrappedSeqC [(+) 1] <*> WrappedSeqC [2] + CollectionAssert.AreEqual (WrappedSeqC [3], res3) + + // Check user defined types implementing IEnumerable don't default to seq<_> + let res4 = WrappedSeqE [(+) 1] <*> WrappedSeqE [3] + CollectionAssert.AreEqual (WrappedSeqE [4], res4) // Idiom brackets from http://www.haskell.org/haskellwiki/Idiom_brackets type Ii = Ii From 13945e8c5fa3d54a8a4de5550aaa400bd6165f15 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sat, 14 Dec 2019 21:27:21 +0100 Subject: [PATCH 18/23] Add test --- tests/FSharpPlus.Tests/General.fs | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/tests/FSharpPlus.Tests/General.fs b/tests/FSharpPlus.Tests/General.fs index b6516e967..8052fd877 100644 --- a/tests/FSharpPlus.Tests/General.fs +++ b/tests/FSharpPlus.Tests/General.fs @@ -1033,7 +1033,11 @@ module Applicative = // Check user defined types implementing IEnumerable don't default to seq<_> let res4 = WrappedSeqE [(+) 1] <*> WrappedSeqE [3] + Assert.IsInstanceOf>> (Some res4) CollectionAssert.AreEqual (WrappedSeqE [4], res4) + let (res5: WrappedSeqE<_>) = WrappedSeqE [(+)] <*> WrappedSeqE [3] <*> WrappedSeqE [2] + Assert.IsInstanceOf>> (Some res5) + CollectionAssert.AreEqual (WrappedSeqE [5], res5) // Idiom brackets from http://www.haskell.org/haskellwiki/Idiom_brackets type Ii = Ii From 7d6f1de8eab8cf8ba6fb728ee39db1e617a45de3 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sat, 14 Dec 2019 21:51:50 +0100 Subject: [PATCH 19/23] Wrap output --- src/FSharpPlus/Functor.fs | 42 +++++++++++++++++++-------------------- 1 file changed, 21 insertions(+), 21 deletions(-) diff --git a/src/FSharpPlus/Functor.fs b/src/FSharpPlus/Functor.fs index 34173b240..bde100b3d 100644 --- a/src/FSharpPlus/Functor.fs +++ b/src/FSharpPlus/Functor.fs @@ -140,31 +140,31 @@ type Return = type Apply = inherit Default1 - static member ``<*>`` (f: Lazy<'T->'U> , _: ref'U>> , x: Lazy<'T> , []_output: Lazy<'U> , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> - static member ``<*>`` (f: seq<_> , _: ref> , x: seq<'T> , []_output: seq<'U> , []_mthd: Apply) = Seq.apply f x : seq<'U> + static member ``<*>`` (f: Lazy<'T->'U> , _: ref'U>> , x: Lazy<'T> , []_output: ref> , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> + static member ``<*>`` (f: seq<_> , _: ref> , x: seq<'T> , []_output: ref> , []_mthd: Apply) = Seq.apply f x : seq<'U> #if !FABLE_COMPILER - static member ``<*>`` (f: IEnumerator<_> , _: ref>, x: IEnumerator<'T>, []_output: IEnumerator<'U> , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> + static member ``<*>`` (f: IEnumerator<_> , _: ref>, x: IEnumerator<'T>, []_output: ref> , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> #endif - static member ``<*>`` (f: list<_> , _: ref> , x: list<'T> , []_output: list<'U> , []_mthd: Apply) = List.apply f x : list<'U> - static member ``<*>`` (f: _ [] , _: ref<_ []> , x: 'T [] , []_output: 'U [] , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] - static member ``<*>`` (f: 'r -> _ , _: ref<'r -> _> , g: _ -> 'T , []_output: 'r -> 'U , []_mthd: Apply) = fun x -> f x (g x) : 'U - static member inline ``<*>`` ((a: 'Monoid, f) , _: ref<'Monoid * _>, (b: 'Monoid, x: 'T) , []_output: 'Monoid * 'U , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U + static member ``<*>`` (f: list<_> , _: ref> , x: list<'T> , []_output: ref> , []_mthd: Apply) = List.apply f x : list<'U> + static member ``<*>`` (f: _ [] , _: ref<_ []> , x: 'T [] , []_output: ref<'U []> , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] + static member ``<*>`` (f: 'r -> _ , _: ref<'r -> _> , g: _ -> 'T , []_output: ref<'r -> 'U> , []_mthd: Apply) = fun x -> f x (g x) : 'U + static member inline ``<*>`` ((a: 'Monoid, f) , _: ref<'Monoid * _>, (b: 'Monoid, x: 'T) , []_output: ref<'Monoid * 'U> , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U #if !FABLE_COMPILER - static member ``<*>`` (f: Task<_> , _: ref> , x: Task<'T> , []_output: Task<'U> , []_mthd: Apply) = Task.apply f x : Task<'U> + static member ``<*>`` (f: Task<_> , _: ref> , x: Task<'T> , []_output: ref> , []_mthd: Apply) = Task.apply f x : Task<'U> #endif - static member ``<*>`` (f: Async<_> , _: ref> , x: Async<'T> , []_output: Async<'U> , []_mthd: Apply) = Async.apply f x : Async<'U> - static member ``<*>`` (f: option<_> , _: ref> , x: option<'T> , []_output: option<'U> , []_mthd: Apply) = Option.apply f x : option<'U> - static member ``<*>`` (f: Result<_,'E> , _: ref> , x: Result<'T,'E> , []_output: Result<'b,'E> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> - static member ``<*>`` (f: Choice<_,'E> , _: ref> , x: Choice<'T,'E> , []_output: Choice<'b,'E> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> - static member inline ``<*>`` (KeyValue(a: 'Key, f), _: ref>, KeyValue(b: 'Key, x: 'T), []_output: KeyValuePair<'Key,'U>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) + static member ``<*>`` (f: Async<_> , _: ref> , x: Async<'T> , []_output: ref> , []_mthd: Apply) = Async.apply f x : Async<'U> + static member ``<*>`` (f: option<_> , _: ref> , x: option<'T> , []_output: ref> , []_mthd: Apply) = Option.apply f x : option<'U> + static member ``<*>`` (f: Result<_,'E> , _: ref> , x: Result<'T,'E> , []_output: ref> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> + static member ``<*>`` (f: Choice<_,'E> , _: ref> , x: Choice<'T,'E> , []_output: ref> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> + static member inline ``<*>`` (KeyValue(a: 'Key, f), _: ref>, KeyValue(b: 'Key, x: 'T), []_output: ref>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) - static member ``<*>`` (f: Map<'Key,_> , _: ref>, x: Map<'Key,'T> , []_output: Map<'Key,'U> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { + static member ``<*>`` (f: Map<'Key,_> , _: ref>, x: Map<'Key,'T> , []_output: ref> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { for KeyValue(k, vf) in f do match Map.tryFind k x with | Some vx -> yield k, vf vx | _ -> () }) - static member ``<*>`` (f: Dictionary<'Key,_>, _: ref>, x: Dictionary<'Key,'T> , []_output: Dictionary<'Key,'U> , []_mthd: Apply) : Dictionary<'Key,'U> = + static member ``<*>`` (f: Dictionary<'Key,_>, _: ref>, x: Dictionary<'Key,'T> , []_output: ref> , []_mthd: Apply) : Dictionary<'Key,'U> = let dct = Dictionary () for KeyValue(k, vf) in f do match x.TryGetValue k with @@ -173,23 +173,23 @@ type Apply = dct #if !FABLE_COMPILER - static member ``<*>`` (f: Expr<'T->'U>, _: ref'U>>, x: Expr<'T>, []_output: Expr<'U>, []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) + static member ``<*>`` (f: Expr<'T->'U>, _: ref'U>>, x: Expr<'T>, []_output: ref>, []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) #endif - static member ``<*>`` (f: ('T->'U) ResizeArray, _: ref<('T->'U) ResizeArray>, x: 'T ResizeArray, []_output: 'U ResizeArray, []_mthd: Apply) = + static member ``<*>`` (f: ('T->'U) ResizeArray, _: ref<('T->'U) ResizeArray>, x: 'T ResizeArray, []_output: ref<'U ResizeArray>, []_mthd: Apply) = ResizeArray (Seq.collect (fun x1 -> Seq.collect (fun x2 -> Seq.singleton (x1 x2)) x) f) : 'U ResizeArray static member inline Invoke (f: '``Applicative<'T -> 'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = - ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_*_ -> _) input1, ref input1, input2, output, mthd) + ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_*_ -> _) input1, ref input1, input2, ref output, mthd) call(Unchecked.defaultof, f, x, Unchecked.defaultof<'``Applicative<'U>``>) static member inline InvokeOnInstance (f: '``Applicative<'T->'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) (f, x)) type Apply with - static member inline ``<*>`` (f: '``Monad<'T->'U>`` , _: ref<'``Monad<'T->'U>``> , x: '``Monad<'T>`` , _output: '``Monad<'U>`` , _mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) - static member inline ``<*>`` (f: '``Applicative<'T->'U>``, _: ref<'``Applicative<'T->'U>``>, x: '``Applicative<'T>``, _output: '``Applicative<'U>``, _mthd:Default1) : '``Applicative<'U>`` = Apply.InvokeOnInstance f x - static member inline ``<*>`` (_: ^t when ^t : null and ^t: struct, _, _: ^u when ^u : null and ^u: struct, _output: ^r when ^r : null and ^r: struct, _mthd: Default1) = id + static member inline ``<*>`` (f: '``Monad<'T->'U>`` , _: ref<'``Monad<'T->'U>``> , x: '``Monad<'T>`` , _output: ref<'``Monad<'U>`` >, _mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) + static member inline ``<*>`` (f: '``Applicative<'T->'U>``, _: ref<'``Applicative<'T->'U>``>, x: '``Applicative<'T>``, _output: ref<'``Applicative<'U>``>, _mthd:Default1) : '``Applicative<'U>`` = Apply.InvokeOnInstance f x + static member inline ``<*>`` (_: ^t when ^t : null and ^t: struct, _, _: ^u when ^u : null and ^u: struct, _output: ref< ^r> when ^r : null and ^r: struct, _mthd: Default1) = id // Functor class ---------------------------------------------------------- From e7e47d45d64adc5eb14b29c930a703f13e1375f8 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sun, 15 Dec 2019 10:57:56 +0100 Subject: [PATCH 20/23] Add failing test --- tests/FSharpPlus.Tests/General.fs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/FSharpPlus.Tests/General.fs b/tests/FSharpPlus.Tests/General.fs index 8052fd877..f5f70dcef 100644 --- a/tests/FSharpPlus.Tests/General.fs +++ b/tests/FSharpPlus.Tests/General.fs @@ -1035,7 +1035,7 @@ module Applicative = let res4 = WrappedSeqE [(+) 1] <*> WrappedSeqE [3] Assert.IsInstanceOf>> (Some res4) CollectionAssert.AreEqual (WrappedSeqE [4], res4) - let (res5: WrappedSeqE<_>) = WrappedSeqE [(+)] <*> WrappedSeqE [3] <*> WrappedSeqE [2] + let res5 = WrappedSeqE [(+)] <*> WrappedSeqE [3] <*> WrappedSeqE [2] Assert.IsInstanceOf>> (Some res5) CollectionAssert.AreEqual (WrappedSeqE [5], res5) From 5e54bd39215fa2cffd0bc31d7ce08f57edfee566 Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sun, 15 Dec 2019 11:06:06 +0100 Subject: [PATCH 21/23] Back to tupled arguments / removing KeyValuePair --- src/FSharpPlus/Functor.fs | 41 +++++++++++++++++++-------------------- 1 file changed, 20 insertions(+), 21 deletions(-) diff --git a/src/FSharpPlus/Functor.fs b/src/FSharpPlus/Functor.fs index bde100b3d..b8f96bdf2 100644 --- a/src/FSharpPlus/Functor.fs +++ b/src/FSharpPlus/Functor.fs @@ -140,31 +140,30 @@ type Return = type Apply = inherit Default1 - static member ``<*>`` (f: Lazy<'T->'U> , _: ref'U>> , x: Lazy<'T> , []_output: ref> , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> - static member ``<*>`` (f: seq<_> , _: ref> , x: seq<'T> , []_output: ref> , []_mthd: Apply) = Seq.apply f x : seq<'U> + static member ``<*>`` ((f: Lazy<'T->'U> , x: Lazy<'T> , _output: Lazy<'U>) , []_mthd: Apply) = Lazy<_>.Create (fun () -> f.Value x.Value) : Lazy<'U> + static member ``<*>`` ((f: seq<_> , x: seq<'T> , _output: seq<'U>) , []_mthd: Apply) = Seq.apply f x : seq<'U> #if !FABLE_COMPILER - static member ``<*>`` (f: IEnumerator<_> , _: ref>, x: IEnumerator<'T>, []_output: ref> , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> + static member ``<*>`` ((f: IEnumerator<_> , x: IEnumerator<'T> , _output: IEnumerator<'U>) , []_mthd: Apply) = Enumerator.map2 id f x : IEnumerator<'U> #endif - static member ``<*>`` (f: list<_> , _: ref> , x: list<'T> , []_output: ref> , []_mthd: Apply) = List.apply f x : list<'U> - static member ``<*>`` (f: _ [] , _: ref<_ []> , x: 'T [] , []_output: ref<'U []> , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] - static member ``<*>`` (f: 'r -> _ , _: ref<'r -> _> , g: _ -> 'T , []_output: ref<'r -> 'U> , []_mthd: Apply) = fun x -> f x (g x) : 'U - static member inline ``<*>`` ((a: 'Monoid, f) , _: ref<'Monoid * _>, (b: 'Monoid, x: 'T) , []_output: ref<'Monoid * 'U> , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U + static member ``<*>`` ((f: list<_> , x: list<'T> , _output: list<'U>) , []_mthd: Apply) = List.apply f x : list<'U> + static member ``<*>`` ((f: _ [] , x: 'T [] , _output: 'U []) , []_mthd: Apply) = Array.collect (fun x1 -> Array.collect (fun x2 -> [|x1 x2|]) x) f : 'U [] + static member ``<*>`` ((f: 'r -> _ , g: _ -> 'T , _output: 'r -> 'U) , []_mthd: Apply) = fun x -> f x (g x) : 'U + static member inline ``<*>`` (((a: 'Monoid, f) , (b: 'Monoid, x: 'T) , _output: 'Monoid * 'U) , []_mthd: Apply) = (Plus.Invoke a b, f x) : 'Monoid *'U #if !FABLE_COMPILER - static member ``<*>`` (f: Task<_> , _: ref> , x: Task<'T> , []_output: ref> , []_mthd: Apply) = Task.apply f x : Task<'U> + static member ``<*>`` ((f: Task<_> , x: Task<'T> , _output: Task<'U>) , []_mthd: Apply) = Task.apply f x : Task<'U> #endif - static member ``<*>`` (f: Async<_> , _: ref> , x: Async<'T> , []_output: ref> , []_mthd: Apply) = Async.apply f x : Async<'U> - static member ``<*>`` (f: option<_> , _: ref> , x: option<'T> , []_output: ref> , []_mthd: Apply) = Option.apply f x : option<'U> - static member ``<*>`` (f: Result<_,'E> , _: ref> , x: Result<'T,'E> , []_output: ref> , []_mthd: Apply) = Result.apply f x : Result<'U,'E> - static member ``<*>`` (f: Choice<_,'E> , _: ref> , x: Choice<'T,'E> , []_output: ref> , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> - static member inline ``<*>`` (KeyValue(a: 'Key, f), _: ref>, KeyValue(b: 'Key, x: 'T), []_output: ref>, []_mthd: Apply) : KeyValuePair<'Key,'U> = KeyValuePair (Plus.Invoke a b, f x) + static member ``<*>`` ((f: Async<_> , x: Async<'T> , _output: Async<'U>) , []_mthd: Apply) = Async.apply f x : Async<'U> + static member ``<*>`` ((f: option<_> , x: option<'T> , _output: option<'U>) , []_mthd: Apply) = Option.apply f x : option<'U> + static member ``<*>`` ((f: Result<_,'E> , x: Result<'T,'E> , _output: Result<'b,'E>) , []_mthd: Apply) = Result.apply f x : Result<'U,'E> + static member ``<*>`` ((f: Choice<_,'E> , x: Choice<'T,'E> , _output: Choice<'b,'E>) , []_mthd: Apply) = Choice.apply f x : Choice<'U,'E> - static member ``<*>`` (f: Map<'Key,_> , _: ref>, x: Map<'Key,'T> , []_output: ref> , []_mthd: Apply) : Map<'Key,'U> = Map (seq { + static member ``<*>`` ((f: Map<'Key,_> , x: Map<'Key,'T> , _output: Map<'Key,'U>) , []_mthd: Apply) : Map<'Key,'U> = Map (seq { for KeyValue(k, vf) in f do match Map.tryFind k x with | Some vx -> yield k, vf vx | _ -> () }) - static member ``<*>`` (f: Dictionary<'Key,_>, _: ref>, x: Dictionary<'Key,'T> , []_output: ref> , []_mthd: Apply) : Dictionary<'Key,'U> = + static member ``<*>`` ((f: Dictionary<'Key,_>, x: Dictionary<'Key,'T> , _output: Dictionary<'Key,'U>) , []_mthd: Apply) : Dictionary<'Key,'U> = let dct = Dictionary () for KeyValue(k, vf) in f do match x.TryGetValue k with @@ -173,23 +172,23 @@ type Apply = dct #if !FABLE_COMPILER - static member ``<*>`` (f: Expr<'T->'U>, _: ref'U>>, x: Expr<'T>, []_output: ref>, []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) + static member ``<*>`` ((f: Expr<'T->'U>, x: Expr<'T>, _output: Expr<'U>), []_mthd: Apply) = Expr.Cast<'U> (Expr.Application (f, x)) #endif - static member ``<*>`` (f: ('T->'U) ResizeArray, _: ref<('T->'U) ResizeArray>, x: 'T ResizeArray, []_output: ref<'U ResizeArray>, []_mthd: Apply) = + static member ``<*>`` ((f: ('T->'U) ResizeArray, x: 'T ResizeArray, _output: 'U ResizeArray), []_mthd: Apply) = ResizeArray (Seq.collect (fun x1 -> Seq.collect (fun x2 -> Seq.singleton (x1 x2)) x) f) : 'U ResizeArray static member inline Invoke (f: '``Applicative<'T -> 'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = let inline call (mthd : ^M, input1: ^I1, input2: ^I2, output: ^R) = - ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : _*_*_*_*_ -> _) input1, ref input1, input2, ref output, mthd) + ((^M or ^I1 or ^I2 or ^R) : (static member ``<*>`` : (_*_*_)*_ -> _) (input1, input2, output), mthd) call(Unchecked.defaultof, f, x, Unchecked.defaultof<'``Applicative<'U>``>) static member inline InvokeOnInstance (f: '``Applicative<'T->'U>``) (x: '``Applicative<'T>``) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) (f, x)) type Apply with - static member inline ``<*>`` (f: '``Monad<'T->'U>`` , _: ref<'``Monad<'T->'U>``> , x: '``Monad<'T>`` , _output: ref<'``Monad<'U>`` >, _mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) - static member inline ``<*>`` (f: '``Applicative<'T->'U>``, _: ref<'``Applicative<'T->'U>``>, x: '``Applicative<'T>``, _output: ref<'``Applicative<'U>``>, _mthd:Default1) : '``Applicative<'U>`` = Apply.InvokeOnInstance f x - static member inline ``<*>`` (_: ^t when ^t : null and ^t: struct, _, _: ^u when ^u : null and ^u: struct, _output: ref< ^r> when ^r : null and ^r: struct, _mthd: Default1) = id + static member inline ``<*>`` ((f: '``Monad<'T->'U>`` , x: '``Monad<'T>`` , _output: '``Monad<'U>`` ), []_mthd:Default2) : '``Monad<'U>`` = Bind.InvokeOnInstance f (fun (x1: 'T->'U) -> Bind.InvokeOnInstance x (fun x2 -> Return.InvokeOnInstance (x1 x2))) + static member inline ``<*>`` ((_: ^t when ^t : null and ^t: struct, _: ^u when ^u : null and ^u: struct, _output: ^r when ^r : null and ^r: struct), _mthd: Default1) = id + static member inline ``<*>`` ((f: '``Applicative<'T->'U>``, x: '``Applicative<'T>``, _output: '``Applicative<'U>``), []_mthd:Default1) : '``Applicative<'U>`` = ((^``Applicative<'T->'U>`` or ^``Applicative<'T>`` or ^``Applicative<'U>``) : (static member (<*>) : _*_ -> _) f, x) // Functor class ---------------------------------------------------------- From c7f967762429cd352fb835d2af61382669cbff3b Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sun, 15 Dec 2019 18:58:12 +0100 Subject: [PATCH 22/23] Comment out failing test --- tests/FSharpPlus.Tests/General.fs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/FSharpPlus.Tests/General.fs b/tests/FSharpPlus.Tests/General.fs index f5f70dcef..903eb1927 100644 --- a/tests/FSharpPlus.Tests/General.fs +++ b/tests/FSharpPlus.Tests/General.fs @@ -1054,9 +1054,9 @@ module IdiomBrackets = let inline iI x = (idiomatic << result) x let res3n4'' = iI ((+) 2) [1;2] Ii - let res3n4''' = iI (+) (result 2) [1;2] Ii // fails to compile when constraints are not properly defined + // let res3n4''' = iI (+) (result 2) [1;2] Ii // fails to compile when constraints are not properly defined Assert.AreEqual ([3;4], res3n4'' ) - Assert.AreEqual ([3;4], res3n4''') + // Assert.AreEqual ([3;4], res3n4''') let output = System.Text.StringBuilder () From a4ab8c354fc1ea4a38d07f1f9807236131f582bd Mon Sep 17 00:00:00 2001 From: Gustavo Leon <1261319+gusty@users.noreply.github.com> Date: Sun, 15 Dec 2019 19:42:28 +0100 Subject: [PATCH 23/23] Comment now failing idiom bracket tests --- tests/FSharpPlus.Tests/General.fs | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/tests/FSharpPlus.Tests/General.fs b/tests/FSharpPlus.Tests/General.fs index 903eb1927..493dd1986 100644 --- a/tests/FSharpPlus.Tests/General.fs +++ b/tests/FSharpPlus.Tests/General.fs @@ -1646,22 +1646,22 @@ module ApplicativeInference = open FSharpPlus.Builders let res3n4'' = iI ((+) 2) [1;2] Ii - let res3n4''' = iI (+) (result 2) [1;2] Ii // *1 - let res18n24' = iI (+) (ZipList(seq [8;4])) (ZipList(seq [10;20])) Ii + // let res3n4''' = iI (+) (result 2) [1;2] Ii // *1 + // let res18n24' = iI (+) (ZipList(seq [8;4])) (ZipList(seq [10;20])) Ii // let res6n7n8' = iI (+) (result 5G ) (ZipList [1;2;3] ) Ii // *1, *2 let res18n14' = iI (+) (ZipList(seq [8;4])) (result 10 ) Ii let safeDiv x y = if y = 0 then None else Some (x y) - let resSome3 = join (iI safeDiv (Some 6) (Some 2) Ii) - let resSome3' = iI safeDiv (Some 6) (Some 2) Ji + // let resSome3 = join (iI safeDiv (Some 6) (Some 2) Ii) + // let resSome3' = iI safeDiv (Some 6) (Some 2) Ji let safeDivBy y = if y = 0 then None else Some (fun x -> x y) let resSome2 = join (result safeDivBy <*> Some 4G) <*> Some 8G - let resSome2' = join ( iI safeDivBy (Some 4G) Ii) <*> Some 8G + // let resSome2' = join ( iI safeDivBy (Some 4G) Ii) <*> Some 8G - let resSome2'' = iI safeDivBy (Some 4G) J (Some 8G) Ii - let resNone = iI safeDivBy (Some 0G) J (Some 8G) Ii - let res16n17 = iI (+) (iI (+) (result 4) [2;3] Ii ) (result 10: _ list) Ii // *1 + // let resSome2'' = iI safeDivBy (Some 4G) J (Some 8G) Ii + // let resNone = iI safeDivBy (Some 0G) J (Some 8G) Ii + // let res16n17 = iI (+) (iI (+) (result 4) [2;3] Ii ) (result 10: _ list) Ii // *1 // *1 These lines fails when Apply.Invoke has no 'or ^'``Applicative<'U>`` ' (output) constraint. // *2 F# 4.1 regression