NAME

contextReaction.pl - Implements a MathObject class for chemical reactions.

DESCRIPTION

This file implements a Context in which chemical reactions can be specified and compared. Reactions can be composed of sums of integer multiples of elements, molecules, ions, compounds, and complexes separated by a right arrow (indicated by -->). Helpful error messages are given when a reaction is not of the correct form. Sums of compounds can be given in any order, but the elements within a compound must be in the order given by the correct answer; e.g., if the correct answer specifies CO_2, then O_2C would be marked incorrect.

To use the context include

loadMacros("contextReaction.pl");
Context("Reaction");

at the top of your PG file, then create Formula objects for your reactions. For example:

$R = Formula("4P + 5O_2 --> 2P_2O_5");

Ions can be specified using ^ to produce superscripts, as in Ca^+2 or Ca^{+2}. Note that the charge may be listed with prefix notation (+2) or postfix notation (2+). By default, TeX will display only the sign of the charge of singly charged ions, e.g., Na^+ and Cl^-. However, the context flag showUnity=>1 can be used to direct TeX to use an alternative notation for singly charged ions, by which the numerical magnitude (1) is displayed along with the sign of the charge, e.g., Na^1+ and Cl^1-. The default value of <showUnity> is zero.

States can be appended to compounds, as in AgCl(s). So you can make reactions like the following:

Ag^+(aq) + Cl^-(aq) --> AgCl(s)

Note that a state can be given by itself, e.g., (l), so you can ask for a student to supply just a state.

Complexes can be formed using square brackets, as in

[CoCl_4(NH_3)_2]^-

These can be used in reactions as with any other compound.

Reactions know how to create their own TeX versions (via $R->TeX), and know how to check student answers (via $R->cmp), just like any other MathObject.

The Reaction Context also allows you to create parts of reactions. E.g., you could create

$products = Formula("4CO_2 + 6H_2O");

which you could use in a problem as follows:

loadMacros("contextReaction.pl");
Context("Reaction");

$reactants = Formula("2C_2H_6 + 7O_2");
$products  = Formula("4CO_2 + 6H_2O");

BEGIN_PGML
[`[$reactants] \longrightarrow`] [_]{$products}{25}.
END_PGML

Note that sums are simplified during comparisons, so that Formula("O + O") and Formula("2O") are equivalent, but Formula("2O") and Formula("O_2") are not equivalent.

All the elements of the periodic table are available within the Reaction Context, as are the states (aq), (s), (l), (g), and (ppt). By default, students are required to include states if the correct answer includes them, but the flag studentsMustUseStates controls this behavior. Setting this flag to 0 will make the use of states optional in student answers. That is, if the correct answer includes states, the student answer need not include them; but if the student does include them, they must be correct. For example, if you set

Context()->flags->set(studentsMustUseStates => 0);

then with the correct answer of Formula("Cl(g)"), a student answer of either Cl or Cl(g) will be marked correct, but an answer of Cl(aq) will be marked false. Note that if the correct answer does not include a state and a student answer does, then it will be marked incorrect regardless of the setting of studentsMustUsetates.

If you need additional terms, like Heat for example, you can add them as variables:

Context()->variables->add(Heat => $context::Reaction::CONSTANT);

Then you can make formulas that include Heat as a term. These "constants" are not allowed to have coefficients or sub- or superscripts, and cannot be combined with compounds except by addition. If you want a term that can be combined in those ways, use $context::Reaction::ELEMENT instead, as in

Context()->variables->add(e => $context::Reaction::ELEMENT);

to allow e for electrons, for example.

If you need to add more states, use $context::Reaction::STATE, as in

Context()->variables->add('(x)' => $context::Reaction::STATE);

to allow a state of (x) for a compound.

By default, the Reaction context checks the student answer against the correct answer in the form the correct answer is given (molecular or condensed structural form). If you want to allow either form, then you can set the flag acceptMolecularForm to 1, in which case, the student's answer is compared first to the original correct answer and then to its molecular form. For example, if the correct answer is (NH_4)_3PO_4, then a student answer of N_3H_12PO_4 would also be considered correct when this flag is set to 1.

You can convert a compound (or every term of a complete reaction) to molecular form using the molecularForm method of any Reaction object. For example

$R = Compute("CH_3CH_2CH_3")->molecularForm;

would make $R be the equivalent of Compute("C_3H_8").

Note that student answers aren't reduced to molecular form when acceptMolecularForm is true. If you want to allow students to enter compounds in any form, you can set the compareMolecular flag to 1, in which case both the correct and student answers are formatted in molecular form internally before they are compared.

The molecular form will have the elements in the order that they first appeared in the compound, and the student must use the same order for their answer to be considered correct. If you want to allow the student to enter the elements in any order, you can set the keepElementOrder flag to 0 which will cause the molecular form to be in alphabetical order. That way, if the student has the correct number of each element, in any order, the two answers will match.

The Reaction context can perform an automatic reduction that combines adjacent elements that are the same. This is controlled by the combineAdjacentElements flag, which is 1 by default. For example,

$R1 = Compute("COOH");
$R2 = Compute("CO_2H");

would equal each other when the flag is set, even when compareMolecular is not set.