ideas-1.0: src/Domain/Math/Power/Exercises.hs
-----------------------------------------------------------------------------
-- Copyright 2011, Open Universiteit Nederland. This file is distributed
-- under the terms of the GNU General Public License. For more information,
-- see the file "LICENSE.txt", which is included in the distribution.
-----------------------------------------------------------------------------
-- |
-- Maintainer : alex.gerdes@ou.nl
-- Stability : provisional
-- Portability : portable (depends on ghc)
--
--
-----------------------------------------------------------------------------
module Domain.Math.Power.Exercises
( -- * Power exercises
simplifyPowerExercise
, powerOfExercise
, nonNegBrokenExpExercise
, calcPowerExercise
) where
import Prelude hiding ( (^) )
import Common.Library
import Common.Utils (distinct)
import Domain.Math.Expr hiding (isPower)
import Domain.Math.Numeric.Views
import Domain.Math.Power.Examples
import Domain.Math.Power.NormViews
import Domain.Math.Power.Rules
import Domain.Math.Power.Strategies
import Domain.Math.Power.Views
-- Exercises
powerExercise :: Exercise Expr
powerExercise = makeExercise
{ status = Provisional
, parser = parseExpr
, navigation = navigator
}
-- | Simplify an expression containing powers as far as possible. This
-- exercise supports the following DWO-applets:
--
-- * HAVO B, hoofdstuk 7, activiteit 1
--
-- * VWO A/C, hoofdstuk 5, activiteit 3 t/m 6
--
-- * VWO B, hoofdstuk 4, activiteit 8, 9, part of 10
simplifyPowerExercise :: Exercise Expr
simplifyPowerExercise = powerExercise
{ exerciseId = describe "simplify expression (powers)" $
newId "algebra.manipulation.exponents.simplify"
, strategy = simplifyPowerStrategy
, ready = predicate isPowerAdd
, suitable = predicateView normPowerMapView
, equivalence = withoutContext (viewEquivalent normPowerMapView)
, examples = level Medium $ concat $
simplerPowers
++ powers1 ++ powers2
++ negExp1 ++ negExp2
++ normPower1 ++ normPower2 ++ normPower3
, ruleOrdering = ruleOrderingWithId $ map getId
[ root2power, subExponents, reciprocalVar, addExponents
, mulExponents, distributePower ]
}
-- | The @powerOfExercise@ is more strict than the 'simplifyPowerExercise'.
-- It only allows one variable experssions. This exercise supports the
-- following DWO-applets:
--
-- * HAVO B, hoofdstuk 7, activiteit 2 and 4
--
-- * VWO A/C, hoofdstuk 5, activiteit part of 10 and 11 and 12
--
-- * VWO B, hoofdstuk 4, activiteit 12 partly, and 13
powerOfExercise :: Exercise Expr
powerOfExercise = powerExercise
{ exerciseId = describe "write as a power of a" $
newId "algebra.manipulation.exponents.powerof"
, ready = predicate isSimplePower
, strategy = simplifyPowerStrategy
, suitable = predicateView normPowerView
, equivalence = withoutContext (viewEquivalent normPowerNonNegRatio)
, examples = level Medium $ concat $ powersOfA ++ powersOfX
++ brokenExp1' ++ brokenExp2 ++ brokenExp3
++ normPower5' ++ normPower6
, ruleOrdering = ruleOrderingWithId $ map getId
[ root2power, addExponents, subExponents, mulExponents
, distributePower, reciprocalVar ]
}
-- | Rewrite power expressions so that they have any negative or broken
-- exponents. Supported DWO-applets:
--
-- * HAVO B, hoofdstuk 7, activiteit 3 and 5
--
-- * VWO A/C, hoofdstuk 5, activiteit 8,9 and part of 10
--
-- * VWO B, hoofdstuk 4, activiteit 11 partly, and 12 partly
nonNegBrokenExpExercise :: Exercise Expr
nonNegBrokenExpExercise = powerExercise
{ exerciseId = describe "write with a non-negative exponent" $
newId "algebra.manipulation.exponents.nonnegative"
, strategy = nonNegBrokenExpStrategy
, ready = predicate (isPower plainNatView)
, suitable = predicateView normPowerNonNegDouble
, equivalence = withoutContext (viewEquivalent normPowerNonNegDouble)
, examples = level Medium $ concat $ nonNegExp ++ nonNegExp2 ++ negExp4 ++ negExp5
++ brokenExp1
++ normPower4' ++ normPower5
, ruleOrdering = ruleOrderingWithId [ getId mulExponents
, getId reciprocalFrac
, getId reciprocalInv
, getId power2root
, getId distributePower ]
}
-- | Calculate the integer number for the given power expression. Supported
-- DWO-applets:
--
-- * VWO A/C, hoofdstuk 5, activiteit 7
--
-- * VWO B, hoofdstuk 4, activiteit 10 partly, 11 partly
calcPowerExercise :: Exercise Expr
calcPowerExercise = powerExercise
{ exerciseId = describe "simplify expression (powers)" $
newId "arithmetic.exponents"
, strategy = calcPowerStrategy
, ready = predicate isPowerAdd
, suitable = predicateView normPowerMapView
, equivalence = withoutContext (viewEquivalent normPowerMapView)
, examples = level Medium $ concat $ negExp3 ++ normPower3' ++ normPower4
}
-- Ready checks
isSimplePower :: Expr -> Bool
isSimplePower (Sym s [Var _, y])
| isPowerSymbol s = y `belongsTo` rationalView
isSimplePower _ = False
isPower :: View Expr a -> Expr -> Bool
isPower v expr =
let xs = snd (from productView expr)
f (Nat 1 :/: a) = g a
f a = g a
g (Sym s [Var _, a]) | isPowerSymbol s = a `belongsTo` v
g (Sym s [x, Nat _]) | isRootSymbol s = isPower v x
g (Sqrt x) = g x
g (Var _) = True
g a = a `belongsTo` rationalView
in distinct (concatMap vars xs) && all f xs
isPowerAdd :: Expr -> Bool
isPowerAdd expr =
let xs = from sumView expr
in all (isPower rationalView) xs && not (applicable calcPowerPlus expr)