dynamic-object-0.2.1: Object-oriented programming with duck typing and singleton classes.

Safe HaskellNone

Data.Object.Dynamic.Examples.PointParticle

Description

Here we use dynamic-object to descibe the concept of point-like particles from classical mechanics. Also read the HSpec tests : https://github.com/nushio3/dynamic-object/blob/master/test/ObjectSpec.hs for more details.

Synopsis

Documentation

data Vec a Source

First, let us create a tiny two-dimensional vector class. We make it an instance of Arbitrary to use them later for tests.

Constructors

Vec a a 

Instances

Typeable1 Vec 
Eq a => Eq (Vec a) 
(Eq (Vec a), Ord a) => Ord (Vec a) 
Show a => Show (Vec a) 
Arbitrary a => Arbitrary (Vec a) 

data Mass Source

Now, let us introduce the concepts of Mass, Velocity, Momentum and KineticEnergy. Any such concepts are described in terms of Member labels.

Constructors

Mass 

data Velocity Source

To define a member with compound types like vector of real numbers, we use UnderlyingReal to ask the object which real value it prefers, then put the response into the type constructors.

We also give a fallback accessor here. If the velocity field is missing, we attempt to re-calculate it from the mass and momentum. Here is how we can do that.

Constructors

Velocity 

data Momentum Source

If the momentum field is missing, we re-calculate it from the mass and velocity.

Constructors

Momentum 

data KineticEnergy Source

kineticEnergy, unless given explicitly, is defined in terms of mass and velocity .

Constructors

KineticEnergy 

mass :: MemberLens o MassSource

Now we define the lenses.

fromMassVelocity :: (Objective o, UseReal o, Fractional real, real ~ UnderlyingReal o) => real -> Vec real -> oSource

We can write functions that would construct a point particle from its mass and velocity. And we can make the function polymorphic over the representation of the real numbers the objects prefer.

fromMassMomentum :: (Objective o, UseReal o, Fractional real, real ~ UnderlyingReal o) => real -> Vec real -> oSource

We can also construct a point particle from its mass and momentum.

laserBeam :: (Objective o, UseReal o, Fractional real, real ~ UnderlyingReal o) => oSource

We define an instance of point-like particle. And again, we can keep it polymorphic, so that anyone can choose its concrete type later, according to their purpose. Thus we will achieve the polymorphic encoding of the knowledge of this world, in Haskell.

>>> (laserBeam :: Object DIT) ^? kineticEnergy
Just 1631.25
>>> (laserBeam :: Object Precise) ^? kineticEnergy
Just (6525 % 4)

Moreover, we can ask Ichiro to sign the ball. Usually, we needed to create a new data-type to add a new field. But with 'dynamic-object' we can do so without changing the type of the ball. So, we can put our precious, one-of-a-kind ball into toybox together with less uncommon balls, and with various other toys. And still, we can safely access the contents of the toybox without runtime errors, and e.g. see which toy is the heaviest.

>>> let (mySpecialBall :: Object DIT) = laserBeam & insert Autograph "Ichiro Suzuki"
>>> let toybox = [laserBeam, mySpecialBall]
>>> let toybox2 = toybox ++ [duck, lens, banana, envelope, ghost]
>>> maximum $ mapMaybe (^?mass) toybox2
5.2

duck :: (Objective o, UseReal o, Fractional real, real ~ UnderlyingReal o) => oSource

lens :: (Objective o, UseReal o, Fractional real, real ~ UnderlyingReal o) => oSource

banana :: (Objective o, UseReal o, Fractional real, real ~ UnderlyingReal o) => oSource