3 people like it.

# Two Logicians

Solves the "Two Logicians" puzzle.

 ``` 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: ``` ``````// Two perfect logicians, S and P, are told that integers x and y have been chosen // such that 1 < x < y and x+y < 100. S is given the value x+y and P is given the // value xy. They then have the following conversation. // // P: I cannot determine the two numbers. // S: I knew that. // P: Now I can determine them. // S: So can I. // // Given that the above statements are true, what are the two numbers? let inOp op f = Seq.groupBy ((<||) op) >> Seq.map snd >> Seq.filter f >> Seq.concat let singleCase op = inOp op (Seq.length >> (=) 1) let all = [for x = 2 to 49 do for y = x + 1 to 99 - x do yield x, y] let spoilP = all |> singleCase (*) |> set all |> inOp (+) (set >> Set.intersect spoilP >> Set.isEmpty) |> singleCase (*) |> singleCase (+) |> Seq.exactlyOne ``````
val inOp : op:('a -> 'b -> 'c) -> f:(seq<'a * 'b> -> bool) -> (seq<'a * 'b> -> seq<'a * 'b>) (requires equality)

Full name: Script.inOp
val op : ('a -> 'b -> 'c) (requires equality)
val f : (seq<'a * 'b> -> bool)
module Seq

from Microsoft.FSharp.Collections
val groupBy : projection:('T -> 'Key) -> source:seq<'T> -> seq<'Key * seq<'T>> (requires equality)

Full name: Microsoft.FSharp.Collections.Seq.groupBy
val map : mapping:('T -> 'U) -> source:seq<'T> -> seq<'U>

Full name: Microsoft.FSharp.Collections.Seq.map
val snd : tuple:('T1 * 'T2) -> 'T2

Full name: Microsoft.FSharp.Core.Operators.snd
val filter : predicate:('T -> bool) -> source:seq<'T> -> seq<'T>

Full name: Microsoft.FSharp.Collections.Seq.filter
val concat : sources:seq<#seq<'T>> -> seq<'T>

Full name: Microsoft.FSharp.Collections.Seq.concat
val singleCase : op:('a -> 'b -> 'c) -> (seq<'a * 'b> -> seq<'a * 'b>) (requires equality)

Full name: Script.singleCase
val length : source:seq<'T> -> int

Full name: Microsoft.FSharp.Collections.Seq.length
val all : (int * int) list

Full name: Script.all
val x : int
val y : int
val spoilP : Set<int * int>

Full name: Script.spoilP
val set : elements:seq<'T> -> Set<'T> (requires comparison)

Full name: Microsoft.FSharp.Core.ExtraTopLevelOperators.set
Multiple items
module Set

from Microsoft.FSharp.Collections

--------------------
type Set<'T (requires comparison)> =
interface IComparable
interface IEnumerable
interface IEnumerable<'T>
interface ICollection<'T>
new : elements:seq<'T> -> Set<'T>
member Add : value:'T -> Set<'T>
member Contains : value:'T -> bool
override Equals : obj -> bool
member IsProperSubsetOf : otherSet:Set<'T> -> bool
member IsProperSupersetOf : otherSet:Set<'T> -> bool
...

Full name: Microsoft.FSharp.Collections.Set<_>

--------------------
new : elements:seq<'T> -> Set<'T>
val intersect : set1:Set<'T> -> set2:Set<'T> -> Set<'T> (requires comparison)

Full name: Microsoft.FSharp.Collections.Set.intersect
val isEmpty : set:Set<'T> -> bool (requires comparison)

Full name: Microsoft.FSharp.Collections.Set.isEmpty
val exactlyOne : source:seq<'T> -> 'T

Full name: Microsoft.FSharp.Collections.Seq.exactlyOne