WeBWorK Problems

How to create a multistep problem from one using PGML and a separate grader

How to create a multistep problem from one using PGML and a separate grader

by Paul Seeburger -
Number of replies: 5
I am trying to create a step-by-step problem that reveals the second step only if the previous step is correct.

I know how to do this with a normal problem:

ANS($ans_eval1 );

$ans_hash1 = $ans_eval1->evaluate($inputs_ref->{ANS_NUM_TO_NAME(1)});

if (1 == $ans_hash1->{score}) {

   rest of the steps in the question

}

However I am trying to modify a problem from PCC that uses its own checker in a macro (and PGML).  How do I check if the previous answer(s) is (are) correct?

I think I just don't really understand how to access the previous answers very clearly in WeBWorK yet.

Here is the code for the problem itself (It's in the Contrib area of the OPL on github.)  See the macro "SolveLinearEquationPCC.pl" for the checker itself.

# WeBWorK problem written by Carl Yao
# Portland Community College
#
# Solve equations like 5x/4-6x=3/8; answer is a fraction or integer.
# Last edited: Kling, 7/18/13; Jordan, 7/10/13; Hughes 7/1/13, Wherry, 6/28/13
# ENDDESCRIPTION

## DBsubject('Algebra')
## DBchapter('Basic Algebra')
## DBsection('Algebraic Expressions')
## KEYWORDS('solve','linear','equation','fraction')
## DBCCSS('6.EE.7','7.EE.4','8.EE.7')
## TitleText1('')
## EditionText1('')
## AuthorText1('')
## Section1('')
## Problem1('')
## Author('Alex Jordan, Carl Yao, Chris Hughes')
## Institution('PCC')

##############################################

DOCUMENT();

loadMacros(
  "PGstandard.pl",
  "MathObjects.pl",
  "PGML.pl",
  "parserAssignment.pl",
  "PCCmacros.pl",
  "answerHints.pl",
  "contextFraction.pl",
  "SolveLinearEquationPCC.pl",
  "PGcourse.pl",
);

##############################################

Context("Fraction");
$var = RandomVariableName();
Context()->variables->are($var => 'Real');
Context()->noreduce('(-x)-y','(-x)+y');

$den1 = random(2,10,2);
$num1 = random(3,9,2);
while (gcd($den1,$num1)!=1) {$num1=random(3,9,2);}

$den2 = 2*$den1;
$num2 = random(3,9,2);
while (gcd($den2,$num2)!=1) {$num2=random(3,9,2);}

#adjust $a's value to make the solution negative
$a=random(5,10,1);
$ans = Fraction($num2*$den1,$num1*$den2-$a*$den1*$den2)->reduce;
@answ = $ans->value;
$ansNum = -$answ[0];
$ansDen = $answ[1];

$frac2 = Fraction($num2,$den2);
$left = Formula("$num1*$var/$den1-$a*$var");
$right = Formula("$frac2");

@vArray = ($var);
@aArray = ($ans);
($ansEqRef, $eqTypesRef) = contextSetup(~~@vArray, ~~@aArray);


##############################################

TEXT(beginproblem());

BEGIN_PGML

[@instructions(~~@vArray)@]**

    [`` [$left]=[$right]  ``]  

    [_______________________________] 

END_PGML

##############################################

answerCheck($ansEqRef, $eqTypesRef);

##############################################

$step1 = $den2*$num1/$den1;
$step2 = $a*$den2;
$step3 = $step1-$step2;
if ($ansDen!=1) {$ansOutput="-\frac{$ansNum}{$ansDen}";}
else {$ansOutput="-$ansNum";}

BEGIN_PGML_SOLUTION

To clear fractions from an equation, multiply each side of the equation by a common denominator. For this problem, a common denominator is [`[$den2]`].

    [``
\begin{aligned}
  \frac{[$num1][$var]}{[$den1]} - [$a][$var] &= \frac{[$num2]}{[$den2]}  \\
  [$den2] \cdot \left(\frac{[$num1][$var]}{[$den1]} - [$a][$var]\right) &= [$den2] \cdot \frac{[$num2]}{[$den2]}  \\
  [$den2] \cdot \frac{[$num1][$var]}{[$den1]} - [$den2] \cdot [$a][$var] &= [$den2] \cdot \frac{[$num2]}{[$den2]}  \\
  [$step1][$var] - [$step2][$var] &= [$num2] \\
  [$step3][$var]             &= [$num2] \\
  \frac{[$step3][$var]}{[$step3]} &= \frac{[$num2]}{[$step3]} \\
  [$var]                     &=  [$ansOutput]
\end{aligned}
    ``]

[@summary($ansEqRef->[0],$left,$right);@]**

END_PGML_SOLUTION

ENDDOCUMENT();

In reply to Paul Seeburger

Re: How to create a multistep problem from one using PGML and a separate grader

by Paul Seeburger -
I think I've figure out how to work with it, although I still feel in the dark about how the student answer variables are accessed in general.

For this type of problem, I can either do my first steps before this problem or I can have other steps after this problem.  To go after, I need to use:

$ans_eval1 = $ansEqRef->[$i]->cmp();

$ans_hash1 = $ans_eval1->evaluate($inputs_ref->{ANS_NUM_TO_NAME(1)});

if (1 == $ans_hash1->{score}) {
BEGIN_TEXT

   Second Part

END_TEXT
}

Paul
In reply to Paul Seeburger

Re: How to create a multistep problem from one using PGML and a separate grader

by Michael Gage -
This is a good method for the approach you are using.

If you would like a better idea of what data is available to you in any problem, temporarily put "PGinfo.pl" in your loadMacros list  and then use

listVariables();  anywhere in the perl code sections of the problems.  (It doesn't go inside TEXT() function -- it prints itself.)

This will print out a complete list of all of the variables that you can access when writing a PG problem.  You won't need most of them of course.

For your original question about writing a sequential problem which hides the second part until the student gets the first part right  there have been a number of approaches starting with the macro file compoundProblem.pl, through compoundProblem5, and the best of the macro packages is called scaffold.pl (completed by Davide Cervone this summer).  


I think it will do what you want.  scaffold.pl is not yet in either the master or the develop version of pg yet.  It is pull request #153 
https://github.com/openwebwork/pg/pull/153 
so you can download it and install it yourself if you wish.

The best version for scaffolded problems that currently exists in the standard "master" distribution of webwork is compoundProblem5 and is described here: 


(scaffold.pl is better -- so I recommend that if at all possible.)
In reply to Michael Gage

Re: How to create a multistep problem from one using PGML and a separate grader

by Davide Cervone -
There is also a newer version of compoundProblem5.pl in the development branch, and you can view it or use the "raw" button to get a copy. It simplifies things considerably and adds PGML support, but it is still not quite so easy as the newer scaffold.pl that Mike mentioned.

There is now some documentation at the top of the compoundProblem5.pl file, with a sample shell of a problem. There is a complete example in the pull request. The older code requires you to keep track of all the answers in all the parts, but the new version doesn't, so the Wiki example Mike linked to is more complicated than it has to be now. There is also a new PROCESS_SCAFFOLD() call that takes care of all the details in the bottom section of the Wiki example.

I just noticed that the documentation at the top of the file calls it scaffold.pl rather than compoundProblem5.pl. I will have to change that, but it was that way because I was going to change the name before I wrote the new scaffold.pl from scratch.
In reply to Davide Cervone

Re: How to create a multistep problem from one using PGML and a separate grader

by Paul Seeburger -
Thanks to both of you, Davide and Mike!

I am curious to find example problems that show each of the new techniques, but I think I have seen one multistep sequential problem that showed blue rows at the bottom of the problem for all the future steps.  These open up as the student progresses through the problem.

Is this standard in the scaffold.pl method?  Is there an option to hide these and have it behave more like the approach I've started using by testing the answer hashes, so the student's view is not cluttered with these lines representing the future steps?

I also want to be sure that my problems will port well to other WeBWorK servers, so I may currently choose the older method since it is most sure to run smoothly (I hope) and make the problems easy to share.

Thanks!

Paul
In reply to Davide Cervone

Re: How to create a multistep problem from one using PGML and a separate grader

by Ted Shifrin -
Thanks to you all for the progress that's been made. In the old days, I could use compoundProblem with the weightedAnswer grader. I have a number of problems where I want to give far more weight to the latter parts of the problem, as opposed to the earlier parts, for example.

Is there any hope for this to wend its way back into working? :)

In the meantime I'm living with compoundProblem5.pl and the students are having all the parts weighted equally.