The Either type represents values with two possibilities: a value of
type Either a b is either Left a or Right b.
The Either type is sometimes used to represent a value which is either correct or an error; by convention, the Left constructor is used to hold an error value and the Right constructor is used to hold a correct value (mnemonic: "right" also means "correct").
Examples
The type Either String Int is the type of values which can be either
a String or an Int. The Left constructor can be used only on
Strings, and the Right constructor can be used only on Ints:
let s = Left "foo" :: Either String IntsLeft "foo"let n = Right 3 :: Either String IntnRight 3:type ss :: Either String Int:type nn :: Either String Int
The fmap from our Functor instance will ignore Left values, but will apply the supplied function to values contained in a Right:
let s = Left "foo" :: Either String Intlet n = Right 3 :: Either String Intfmap (*2) sLeft "foo"fmap (*2) nRight 6
The Monad instance for Either allows us to chain together multiple actions which may fail, and fail overall if any of the individual steps failed. First we'll write a function that can either parse an Int from a Char, or fail.
import Data.Char ( digitToInt, isDigit ):{ let parseEither :: Char -> Either String Int parseEither c | isDigit c = Right (digitToInt c) | otherwise = Left "parse error":}
The following should work, since both '1' and '2' can be
parsed as Ints.
:{ let parseMultiple :: Either String Int parseMultiple = do x <- parseEither '1' y <- parseEither '2' return (x + y):}
parseMultipleRight 3
But the following should fail overall, since the first operation where
we attempt to parse 'm' as an Int will fail:
:{ let parseMultiple :: Either String Int parseMultiple = do x <- parseEither 'm' y <- parseEither '2' return (x + y):}
parseMultipleLeft "parse error"
Instances170Bifoldable, Bifoldable1, Bifunctor, Bitraversable, Eq2, Ord2, …
Bifoldable EitherDefined in base-4.22.0.0 · Data.BifoldableBifoldable1 EitherDefined in base-4.22.0.0 · Data.Bifoldable1Bifunctor EitherDefined in base-4.22.0.0 · Data.BifunctorBitraversable EitherDefined in base-4.22.0.0 · Data.BitraversableEq2 EitherDefined in base-4.22.0.0 · Data.Functor.ClassesOrd2 EitherDefined in base-4.22.0.0 · Data.Functor.ClassesRead2 EitherDefined in base-4.22.0.0 · Data.Functor.ClassesShow2 EitherDefined in base-4.22.0.0 · Data.Functor.ClassesNFData2 EitherDefined in deepseq-1.5.1.0 · Control.DeepSeqArbitrary2 EitherDefined in QuickCheck-2.18.0.0 · Test.QuickCheck.ArbitraryHashable2 EitherDefined in hashable-1.5.1.0 · Data.Hashable.ClassAssoc EitherDefined in assoc-1.1.1 · Data.Bifunctor.AssocSwap EitherDefined in assoc-1.1.1 · Data.Bifunctor.SwapBitraversable1 EitherDefined in semigroupoids-6.0.2 · Data.Semigroup.Traversable.ClassBicrosswalk EitherDefined in semialign-1.4 · Data.CrosswalkFromJSON2 EitherDefined in aeson-2.2.5.1 · Data.Aeson.Types.FromJSONToJSON2 EitherDefined in aeson-2.2.5.1 · Data.Aeson.Types.ToJSONInvariant2 EitherDefined in invariant-0.6.5 · Data.Functor.InvariantLifting2 Binary EitherDefined in constraints-0.14.4 · Data.Constraint.LiftingLifting2 NFData EitherDefined in constraints-0.14.4 · Data.Constraint.LiftingLifting2 Eq EitherDefined in constraints-0.14.4 · Data.Constraint.LiftingLifting2 Ord EitherDefined in constraints-0.14.4 · Data.Constraint.LiftingLifting2 Read EitherDefined in constraints-0.14.4 · Data.Constraint.LiftingLifting2 Show EitherDefined in constraints-0.14.4 · Data.Constraint.LiftingLifting2 Hashable EitherDefined in constraints-0.14.4 · Data.Constraint.LiftingBinary a => Lifting Binary (Either a)Defined in constraints-0.14.4 · Data.Constraint.LiftingNFData a => Lifting NFData (Either a)Defined in constraints-0.14.4 · Data.Constraint.LiftingEq a => Lifting Eq (Either a)Defined in constraints-0.14.4 · Data.Constraint.LiftingOrd a => Lifting Ord (Either a)Defined in constraints-0.14.4 · Data.Constraint.LiftingRead a => Lifting Read (Either a)Defined in constraints-0.14.4 · Data.Constraint.LiftingShow a => Lifting Show (Either a)Defined in constraints-0.14.4 · Data.Constraint.LiftingHashable a => Lifting Hashable (Either a)Defined in constraints-0.14.4 · Data.Constraint.LiftingGeneric1 (Either a)Defined in ghc-internal-9.1401.0 · GHC.Internal.GenericsMonadError e (Either e)Defined in mtl-2.3.1 · Control.Monad.Error.Class() :=> Applicative (Either a)Defined in constraints-0.14.4 · Data.Constraint() :=> Functor (Either a)Defined in constraints-0.14.4 · Data.Constraint() :=> Monad (Either a)Defined in constraints-0.14.4 · Data.Constraint(Lift a, Lift b) => Lift (Either a b)Defined in ghc-internal-9.1401.0 · GHC.Internal.TH.LiftPrettyDefaultBy config (Either a b) => PrettyBy config (Either a b)Defined in plutus-core-1.70.0.0 · PlutusPrelude · orphan(PrettyBy config a, PrettyBy config b) => DefaultPrettyBy config (Either a b)Defined in plutus-core-1.70.0.0 · PlutusPrelude · orphan(ToBuiltinMeaning uni fun1, ToBuiltinMeaning uni fun2, Default (BuiltinSemanticsVariant fun1), Default (BuiltinSemanticsVariant fun2)) => ToBuiltinMeaning uni (Either fun1 fun2)Defined in plutus-core-1.70.0.0 · PlutusCore.Examples.Builtins · orphan(Typeable DefaultUni a, Typeable DefaultUni b, Lift DefaultUni a, Lift DefaultUni b) => Lift DefaultUni (Either a b)Defined in plutus-tx-1.70.0.0 · PlutusTx.Lift.Instances · orphanMonad (Either e)Defined in ghc-internal-9.1401.0 · GHC.Internal.Data.EitherFunctor (Either a)Defined in ghc-internal-9.1401.0 · GHC.Internal.Data.EitherMonadFix (Either e)Defined in ghc-internal-9.1401.0 · GHC.Internal.Control.Monad.FixApplicative (Either e)Defined in ghc-internal-9.1401.0 · GHC.Internal.Data.EitherFoldable (Either a)Defined in ghc-internal-9.1401.0 · GHC.Internal.Data.FoldableTraversable (Either a)Defined in ghc-internal-9.1401.0 · GHC.Internal.Data.TraversableEq a => Eq1 (Either a)Defined in base-4.22.0.0 · Data.Functor.ClassesOrd a => Ord1 (Either a)Defined in base-4.22.0.0 · Data.Functor.ClassesRead a => Read1 (Either a)Defined in base-4.22.0.0 · Data.Functor.ClassesShow a => Show1 (Either a)Defined in base-4.22.0.0 · Data.Functor.ClassesNFData a => NFData1 (Either a)Defined in deepseq-1.5.1.0 · Control.DeepSeqe ~ SomeException => MonadCatch (Either e)Defined in exceptions-0.10.11 · Control.Monad.Catche ~ SomeException => MonadMask (Either e)Defined in exceptions-0.10.11 · Control.Monad.Catche ~ SomeException => MonadThrow (Either e)Defined in exceptions-0.10.11 · Control.Monad.CatchArbitrary a => Arbitrary1 (Either a)Defined in QuickCheck-2.18.0.0 · Test.QuickCheck.ArbitraryHashable a => Hashable1 (Either a)Defined in hashable-1.5.1.0 · Data.Hashable.ClassAlt (Either a)Defined in semigroupoids-6.0.2 · Data.Functor.AltApply (Either a)Defined in semigroupoids-6.0.2 · Data.Functor.Bind.ClassBind (Either a)Defined in semigroupoids-6.0.2 · Data.Functor.Bind.ClassExtend (Either a)Defined in semigroupoids-6.0.2 · Data.Functor.ExtendMonoid e => Filterable (Either e)Defined in witherable-0.5 · WitherableMonoid e => Witherable (Either e)Defined in witherable-0.5 · WitherableFromJSON a => FromJSON1 (Either a)Defined in aeson-2.2.5.1 · Data.Aeson.Types.FromJSONToJSON a => ToJSON1 (Either a)Defined in aeson-2.2.5.1 · Data.Aeson.Types.ToJSON(Default (BuiltinSemanticsVariant fun1), Default (BuiltinSemanticsVariant fun2)) => Default (BuiltinSemanticsVariant (Either fun1 fun2))Defined in plutus-core-1.70.0.0 · PlutusCore.Examples.Builtins · orphanMonadFailure (Either a)Defined in basement-0.0.16 · Basement.MonadInvariant (Either a)Defined in invariant-0.6.5 · Data.Functor.InvariantApplicative (Either a)Defined in plutus-tx-1.70.0.0 · PlutusTx.ApplicativeFunctor (Either c)Defined in plutus-tx-1.70.0.0 · PlutusTx.FunctorFoldable (Either c)Defined in plutus-tx-1.70.0.0 · PlutusTx.FoldableTraversable (Either c)Defined in plutus-tx-1.70.0.0 · PlutusTx.TraversableSelective (Either e)Defined in selective-0.7.0.1 · Control.SelectiveMonadBase (Either e) (Either e)Defined in transformers-base-0.4.6.1 · Control.Monad.BaseMonadBaseControl (Either e) (Either e)Defined in monad-control-1.0.3.1 · Control.Monad.Trans.ControlFrom (Maybe a) (Either () a)Defined in basement-0.0.16 · Basement.FromSerialiseHFC xs => DecodeDisk (HardForkBlock xs) (ByteString -> Either DecoderError (HardForkBlock xs))Defined in ouroboros-consensus-4.2.1.0 · Ouroboros.Consensus.HardFork.Combinator.Serialisation.SerialiseDisk · orphan(Bounded a, Bounded b) => Bounded (Either a b)Defined in plutus-core-1.70.0.0 · PlutusCore.Examples.Builtins · orphan(Eq a, Eq b, Bounded a, Bounded b, Enum a, Enum b) => Enum (Either a b)Defined in plutus-core-1.70.0.0 · PlutusCore.Examples.Builtins · orphan(Eq a, Eq b) => Eq (Either a b)Defined in ghc-internal-9.1401.0 · GHC.Internal.Data.Either(Data a, Data b) => Data (Either a b)Defined in ghc-internal-9.1401.0 · GHC.Internal.Data.Data(Ord a, Ord b) => Ord (Either a b)Defined in ghc-internal-9.1401.0 · GHC.Internal.Data.Either(Read a, Read b) => Read (Either a b)Defined in ghc-internal-9.1401.0 · GHC.Internal.Data.Either(Show a, Show b) => Show (Either a b)Defined in ghc-internal-9.1401.0 · GHC.Internal.Data.Either(Bounded a, Bounded b, Ix a, Ix b) => Ix (Either a b)Defined in plutus-core-1.70.0.0 · PlutusCore.Examples.Builtins · orphanGeneric (Either a b)Defined in ghc-internal-9.1401.0 · GHC.Internal.GenericsSemigroup (Either a b)Defined in ghc-internal-9.1401.0 · GHC.Internal.Data.Either(NFData a, NFData b) => NFData (Either a b)Defined in deepseq-1.5.1.0 · Control.DeepSeq(Pretty a, Pretty b) => Pretty (Either a b)Defined in pretty-1.1.3.6 · Text.PrettyPrint.Annotated.HughesPJClass(Pretty a, Pretty b) => Pretty (Either a b)Defined in pretty-1.1.3.6 · Text.PrettyPrint.HughesPJClass(Binary a, Binary b) => Binary (Either a b)Defined in binary-0.8.9.3 · Data.Binary.Class(Finite a, Finite b) => Finite (Either a b)Defined in random-1.3.1 · System.Random.GFinite(Finite a, Uniform a, Finite b, Uniform b) => Uniform (Either a b)Defined in random-1.3.1 · System.Random.Internal(Arbitrary a, Arbitrary b) => Arbitrary (Either a b)Defined in QuickCheck-2.18.0.0 · Test.QuickCheck.Arbitrary(CoArbitrary a, CoArbitrary b) => CoArbitrary (Either a b)Defined in QuickCheck-2.18.0.0 · Test.QuickCheck.Arbitrary(Function a, Function b) => Function (Either a b)Defined in QuickCheck-2.18.0.0 · Test.QuickCheck.Function(Pretty a, Pretty b) => Pretty (Either a b)Defined in plutus-core-1.70.0.0 · PlutusPrelude · orphan(Hashable a, Hashable b) => Hashable (Either a b)Defined in hashable-1.5.1.0 · Data.Hashable.Class(FromJSON a, FromJSON b) => FromJSON (Either a b)Defined in aeson-2.2.5.1 · Data.Aeson.Types.FromJSON(ToJSON a, ToJSON b) => ToJSON (Either a b)Defined in aeson-2.2.5.1 · Data.Aeson.Types.ToJSON(Serialize a, Serialize b) => Serialize (Either a b)Defined in cereal-0.5.8.3 · Data.Serialize(FromHttpApiData a, FromHttpApiData b) => FromHttpApiData (Either a b)Defined in http-api-data-0.7 · Web.Internal.HttpApiDataExample1 expression parseUrlPiece "Right 123" :: Either Text (Either String Int)Right (Right 123)
(ToHttpApiData a, ToHttpApiData b) => ToHttpApiData (Either a b)Defined in http-api-data-0.7 · Web.Internal.HttpApiDataExample2 expressions toUrlPiece (Left "err" :: Either String Int)"left err"toUrlPiece (Right 3 :: Either String Int)"right 3"
(Serialise a, Serialise b) => Serialise (Either a b)Defined in serialise-0.2.6.1 · Codec.Serialise.Class(NormalForm l, NormalForm r) => NormalForm (Either l r)Defined in basement-0.0.16 · Basement.NormalForm(Absurd a, Absurd b) => Absurd (Either a b)Defined in boring-0.2.2.1 · Data.Boring(Finite a, Finite b) => Finite (Either a b)Defined in universe-base-1.1.4 · Data.Universe.Class(Universe a, Universe b) => Universe (Either a b)Defined in universe-base-1.1.4 · Data.Universe.Class(MemPack a, MemPack b) => MemPack (Either a b)Defined in mempack-0.2.1.0 · Data.MemPack(NoThunks a, NoThunks b) => NoThunks (Either a b)Defined in nothunks-0.3.1 · NoThunks.ClassCorecursive (Either a b)Defined in recursion-schemes-5.2.3 · Data.Functor.FoldableRecursive (Either a b)Defined in recursion-schemes-5.2.3 · Data.Functor.Foldable(FromCBOR a, FromCBOR b) => FromCBOR (Either a b)Defined in cardano-binary-1.9.1.0 · Cardano.Binary.FromCBOR(ToCBOR a, ToCBOR b) => ToCBOR (Either a b)Defined in cardano-binary-1.9.1.0 · Cardano.Binary.ToCBOR(HeapWords a, HeapWords b) => HeapWords (Either a b)Defined in heapwords-0.1.0.2 · Cardano.HeapWordsFromField a => FromField (Either Field a)Defined in cassava-0.5.4.1 · Data.Csv.Conversion(PrettyVal a, PrettyVal b) => PrettyVal (Either a b)Defined in pretty-show-1.10 · Text.Show.PrettyVal(Lexicographic a, Lexicographic b) => Lexicographic (Either a b)Defined in vector-algorithms-0.9.1.0 · Data.Vector.Algorithms.AmericanFlagMonoFoldable (Either a b)Defined in mono-traversable-1.0.21.0 · Data.MonoTraversableMonoFunctor (Either a b)Defined in mono-traversable-1.0.21.0 · Data.MonoTraversableMonoTraversable (Either a b)Defined in mono-traversable-1.0.21.0 · Data.MonoTraversableMonoPointed (Either a b)Defined in mono-traversable-1.0.21.0 · Data.MonoTraversable(FromData a, FromData b) => FromData (Either a b)Defined in plutus-tx-1.70.0.0 · PlutusTx.IsData.Instances · orphan(ToData a, ToData b) => ToData (Either a b)Defined in plutus-tx-1.70.0.0 · PlutusTx.IsData.Instances · orphan(UnsafeFromData a, UnsafeFromData b) => UnsafeFromData (Either a b)Defined in plutus-tx-1.70.0.0 · PlutusTx.IsData.Instances · orphan(Eq a, Eq b) => Eq (Either a b)Defined in plutus-tx-1.70.0.0 · PlutusTx.Eq · orphan(Ord a, Ord b) => Ord (Either a b)Defined in plutus-tx-1.70.0.0 · PlutusTx.Ord · orphan(Show a, Show b) => Show (Either a b)Defined in plutus-tx-1.70.0.0 · PlutusTx.Show · orphan(DecCBOR a, DecCBOR b) => DecCBOR (Either a b)Defined in cardano-ledger-binary-1.9.1.0 · Cardano.Ledger.Binary.Decoding.DecCBOR(EncCBOR a, EncCBOR b) => EncCBOR (Either a b)Defined in cardano-ledger-binary-1.9.1.0 · Cardano.Ledger.Binary.Encoding.EncCBOR(ToExpr a, ToExpr b) => ToExpr (Either a b)Defined in tree-diff-0.4.1 · Data.TreeDiff.Class(Arbitrary l, Arbitrary r) => Arbitrary (Either l r)Defined in foundation-0.0.30 · Foundation.Check.Arbitrary(HasBlueprintDefinition a, HasSchemaDefinition a referencedTypes, HasBlueprintDefinition b, HasSchemaDefinition b referencedTypes) => HasBlueprintSchema (Either a b) referencedTypesDefined in plutus-tx-1.70.0.0 · PlutusTx.IsData.Instances · orphanTypeable DefaultUni EitherDefined in plutus-tx-1.70.0.0 · PlutusTx.Lift.Instances · orphan(Eq a, Eq b) :=> Eq (Either a b)Defined in constraints-0.14.4 · Data.Constraint(Ord a, Ord b) :=> Ord (Either a b)Defined in constraints-0.14.4 · Data.Constraint(Read a, Read b) :=> Read (Either a b)Defined in constraints-0.14.4 · Data.Constraint(Show a, Show b) :=> Show (Either a b)Defined in constraints-0.14.4 · Data.ConstraintStrict (Either a b) (Either a b)Defined in strict-0.5.1 · Data.Strict.ClassesFrom (Either a b) (These a b)Defined in basement-0.0.16 · Basement.From(a ~ a', b ~ b') => Each (Either a a') (Either b b') a bDefined in microlens-0.4.14.0 · Lens.Micro.Internal(a ~ a', b ~ b') => Each (Either a a') (Either b b') a bDefined in lens-5.3.6 · Control.Lens.Each(FoldableWithIndex i f, FoldableWithIndex j g) => FoldableWithIndex (Either i j) (Product f g)Defined in indexed-traversable-0.1.5 · WithIndex(FoldableWithIndex i f, FoldableWithIndex j g) => FoldableWithIndex (Either i j) (Sum f g)Defined in indexed-traversable-0.1.5 · WithIndex(FoldableWithIndex i f, FoldableWithIndex j g) => FoldableWithIndex (Either i j) (f :*: g)Defined in indexed-traversable-0.1.5 · WithIndex(FoldableWithIndex i f, FoldableWithIndex j g) => FoldableWithIndex (Either i j) (f :+: g)Defined in indexed-traversable-0.1.5 · WithIndex(FunctorWithIndex i f, FunctorWithIndex j g) => FunctorWithIndex (Either i j) (Product f g)Defined in indexed-traversable-0.1.5 · WithIndex(FunctorWithIndex i f, FunctorWithIndex j g) => FunctorWithIndex (Either i j) (Sum f g)Defined in indexed-traversable-0.1.5 · WithIndex(FunctorWithIndex i f, FunctorWithIndex j g) => FunctorWithIndex (Either i j) (f :*: g)Defined in indexed-traversable-0.1.5 · WithIndex(FunctorWithIndex i f, FunctorWithIndex j g) => FunctorWithIndex (Either i j) (f :+: g)Defined in indexed-traversable-0.1.5 · WithIndex(TraversableWithIndex i f, TraversableWithIndex j g) => TraversableWithIndex (Either i j) (Product f g)Defined in indexed-traversable-0.1.5 · WithIndex(TraversableWithIndex i f, TraversableWithIndex j g) => TraversableWithIndex (Either i j) (Sum f g)Defined in indexed-traversable-0.1.5 · WithIndex(TraversableWithIndex i f, TraversableWithIndex j g) => TraversableWithIndex (Either i j) (f :*: g)Defined in indexed-traversable-0.1.5 · WithIndex(TraversableWithIndex i f, TraversableWithIndex j g) => TraversableWithIndex (Either i j) (f :+: g)Defined in indexed-traversable-0.1.5 · WithIndex(RepeatWithIndex i f, RepeatWithIndex j g) => RepeatWithIndex (Either i j) (Product f g)Defined in semialign-1.4 · Data.Semialign.Internal(SemialignWithIndex i f, SemialignWithIndex j g) => SemialignWithIndex (Either i j) (Product f g)Defined in semialign-1.4 · Data.Semialign.Internal(ZipWithIndex i f, ZipWithIndex j g) => ZipWithIndex (Either i j) (Product f g)Defined in semialign-1.4 · Data.Semialign.Internal(FilterableWithIndex i f, FilterableWithIndex j g) => FilterableWithIndex (Either i j) (Product f g)Defined in witherable-0.5 · Witherable(FilterableWithIndex i f, FilterableWithIndex j g) => FilterableWithIndex (Either i j) (Sum f g)Defined in witherable-0.5 · Witherable(WitherableWithIndex i f, WitherableWithIndex j g) => WitherableWithIndex (Either i j) (Product f g)Defined in witherable-0.5 · Witherable(WitherableWithIndex i f, WitherableWithIndex j g) => WitherableWithIndex (Either i j) (Sum f g)Defined in witherable-0.5 · Witherabletype Rep (Either a b) = D1 ('MetaDataDefined in ghc-internal-9.1401.0 · GHC.Internal.Generics"Either"
"GHC.Internal.Data.Either"
"ghc-internal"
'False) (C1 ('MetaCons"Left"
'PrefixI 'False) (S1 ('MetaSel 'Nothing 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedLazy) (Rec0 a)) :+: C1 ('MetaCons"Right"
'PrefixI 'False) (S1 ('MetaSel 'Nothing 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedLazy) (Rec0 b)))type Rep1 (Either a) = D1 ('MetaDataDefined in ghc-internal-9.1401.0 · GHC.Internal.Generics"Either"
"GHC.Internal.Data.Either"
"ghc-internal"
'False) (C1 ('MetaCons"Left"
'PrefixI 'False) (S1 ('MetaSel 'Nothing 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedLazy) (Rec0 a)) :+: C1 ('MetaCons"Right"
'PrefixI 'False) (S1 ('MetaSel 'Nothing 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedLazy) Par1))type Failure (Either a) = aDefined in basement-0.0.16 · Basement.Monadtype Base (Either a b) = Const (Either a b)Defined in recursion-schemes-5.2.3 · Data.Functor.FoldableExample boring stub for non-recursive data types
type StM (Either e) a = aDefined in monad-control-1.0.3.1 · Control.Monad.Trans.Controltype Element (Either a b) = bDefined in mono-traversable-1.0.21.0 · Data.MonoTraversabledata BuiltinSemanticsVariant (Either fun1 fun2)PairV (BuiltinSemanticsVariant fun1) (BuiltinSemanticsVariant fun2)
type CostingPart uni (Either fun1 fun2) = (CostingPart uni fun1, CostingPart uni fun2)Defined in plutus-core-1.70.0.0 · PlutusCore.Examples.Builtins · orphan