69 lines
1.6 KiB
Idris
69 lines
1.6 KiB
Idris
||| like Data.So, but for False instead.
|
|
||| less messing about with `not` (and constantly rewriting everything)
|
|
||| or `Not` (unfriendly to proof search).
|
|
module Quox.No
|
|
|
|
import public Data.So
|
|
import public Quox.Decidable
|
|
import Data.Bool
|
|
|
|
public export
|
|
data No : Pred Bool where
|
|
Ah : No False
|
|
|
|
export Uninhabited (No True) where uninhabited _ impossible
|
|
|
|
export %inline
|
|
soNo : So b -> No b -> Void
|
|
soNo Oh Ah impossible
|
|
|
|
|
|
private
|
|
0 orFalse : (a, b : Bool) -> (a || b) = False -> (a = False, b = False)
|
|
orFalse a b eq1 with (a || b) proof eq2
|
|
orFalse False False Refl | False = (Refl, Refl)
|
|
orFalse False True Refl | False = absurd eq2
|
|
orFalse True False Refl | False = absurd eq2
|
|
orFalse True True Refl | False = absurd eq2
|
|
|
|
parameters {0 a, b : Bool}
|
|
export %inline
|
|
noOr : No (a || b) -> (No a, No b)
|
|
noOr n with 0 (a || b) proof eq
|
|
noOr Ah | False =
|
|
let 0 eqs = orFalse a b eq in
|
|
(rewrite fst eqs in Ah, rewrite snd eqs in Ah)
|
|
|
|
export %inline
|
|
noOr1 : No (a || b) -> No a
|
|
noOr1 = fst . noOr
|
|
|
|
export %inline
|
|
noOr2 : No (a || b) -> No b
|
|
noOr2 = snd . noOr
|
|
|
|
|
|
infixr 1 `orNo`
|
|
export %inline
|
|
orNo : No a -> No b -> No (a || b)
|
|
orNo Ah Ah = Ah
|
|
|
|
export %inline
|
|
nchoose : (b : Bool) -> Either (So b) (No b)
|
|
nchoose True = Left Oh
|
|
nchoose False = Right Ah
|
|
|
|
|
|
private
|
|
0 notFalseTrue : (a : Bool) -> not a = True -> a = False
|
|
notFalseTrue False Refl = Refl
|
|
|
|
export %inline
|
|
soNot : So (not a) -> No a
|
|
soNot x with 0 (not a) proof eq
|
|
soNot Oh | True =
|
|
rewrite notFalseTrue a eq in Ah
|
|
|
|
export %inline
|
|
soNot' : So a -> No (not a)
|
|
soNot' Oh = Ah
|