WeBWorK Problems

Can't generate enough valid points for comparison error

Can't generate enough valid points for comparison error

by Paul Seeburger -
Number of replies: 1
Hello,

I am having trouble with a problem I created in WeBWorK 2.9 that does not work properly in the current version of WeBWorK on the U of R server.

It uses bizarro arithmetic to try to be sure students simplify entries in a multianswer construct.

For some reason, even when all answers are correct, I get back the error "" on the multianswer components of the problem every time.

Here is the code for the problem:

## DESCRIPTION
## Differential equation solved using Variation of Parameters
## ENDDESCRIPTION


## DBsubject(Differential equations)
## DBchapter(Higher order differential equations)
## DBsection(Variation of parameters)
## Date(3/12/2015)
## Institution(Monroe Community College)
## Author(Paul Seeburger)
## Level(2)
## KEYWORDS('differential equation','second order','linear','nonhomogeneous','variation of parameters')
## adapted from: IndianaDiffEq/setDiffEQ10Linear2ndOrderNonhom/ur_de_10_16.pg

DOCUMENT() ;

loadMacros(
"PGstandard.pl",
"MathObjects.pl",
"PGmatrixmacros.pl",
"parserPopUp.pl",
"parserMultiAnswer.pl",
"weightedGrader.pl",
"bizarroArithmetic.pl",
"PGunion.pl",
"PGcourse.pl",
#"PGdiffeqmacros.pl"
) ;
############
TEXT(beginproblem()) ;

Context("Numeric");

Context()->variables->are(
't'=>["Real", limits=>[-2,2]], 'y'=>["Real", limits=>[-2,2]]);
#, 'a'=>'Parameter','b'=>'Parameter');
#Context()->variables->remove('x');
Context()->functions->set( atan => {TeX => '\arctan'} );

# root of the characteristic equation
$r = Real(non_zero_random(-5,5,1));
$a = -2*$r;
$b = $r**2;
$c = Real(non_zero_random(-20,20,.5));
$ch = Real("-1*$c/2");
# $e = exp(1);
# $ans = Compute("($c/2)*(($e)**($r*t))");

$showPartialCorrectAnswers = 1 ;

$yp = Compute("e^($r t)($ch ln(t^2 + 1) + $c t arctan(t))")->reduce;


Context("Numeric");

Context()->variables->are(
't'=>["Real", limits=>[-2,2]], 'y'=>["Real", limits=>[-2,2]]);
#Context()->variables->remove('x');
Context()->functions->set( atan => {TeX => '\arctan'} );
#Context()->flags->set( checkUndefinedPoints=>1);

$a11 = Formula("e^($r t)");
#$a11->{test_at} = [[-2],[-1],[0],[1],[2]];
$a12 = Formula("t e^($r t)");
$a21 = Formula("$r e^($r t)");
$a22 = Formula("e^($r t)(1 + $r t)");

$n = Real("2*$r");
$wronskian = Formula("e^($n t)"); #Compute

$b11 = Real("0"); #Formula("0t");
$b12 = Formula("t e^($r t)");
$b21 = Formula("$c e^($r t)/(t^2+1)");
$b22 = Formula("e^($r t)(1 + $r t)");

$n2 = Real("-1*$c");
$w1 = Formula("$n2 t e^($n t)/(t^2+1)"); #Compute

$c11 = Formula("e^($r t)");
$c12 = Real("0"); #Formula("0t");
$c21 = Formula("$r e^($r t)");
$c22 = Formula("$c e^($r t)/(t^2+1)");

$w2 = Formula("$c e^($n t)/(t^2+1)"); #Compute

$u1p = Formula("$n2 t/(t^2+1)"); #Compute
$u2p = Formula("$c/(t^2+1)"); #Compute

$u1 = Formula("$n2/2 * ln(t^2 + 1)")->reduce; #Compute
$u2 = Formula("$c arctan(t)"); #Compute

#$yp = Compute("$ch e^($r t)ln(t^2 + 1) + $c t arctan(t)")->reduce;


$multians1 = MultiAnswer($a11, $a12, $a21, $a22, $wronskian, $b11, $b12, $b21, $b22, $w1, $c11, $c12, $c21, $c22, $w2, $u1p, $u2p, $u1, $u2)->with(

singleResult => 0, # I cannot get this problem to work well with a single result since it would not show students which parts are correct and which are incorrect. Maybe change in the future, once this process is easier.
allowBlankAnswers => 1,
checkTypes => 0,
# The formatting has not been expanded to include the second and third determinants
# This is not important on this problem since we cannot display the problem this way anyway.
format => "<table border='0' cellspacing='20'>
<tr><td> %s </td><td>&nbsp; %s </td> </tr>
<tr><td> %s </td><td>&nbsp; %s </td> </tr>
<tr><td> &nbsp; = %s </td></tr>
</table>",
tex_format => "\left\lbrack\begin{array}{rr} %s & %s \\ %s & %s \end{array}\right\rbrack = %s",

checker => sub {</font></div> <div><font face="courier new, courier, monospace"> my ( $correct, $student, $self, $ans) = @_;</font></div> <div><font face="courier new, courier, monospace"> my @c = @{$correct};
my @s = @{$student};
my @score = ();

Context()->operators->set(
'/' => {class => 'bizarro::BOP::divide', isCommand => 1},
'/ ' => {class => 'bizarro::BOP::divide', isCommand => 1},
' /' => {class => 'bizarro::BOP::divide', isCommand => 1},
'//' => {class => 'bizarro::BOP::divide', isCommand => 1},
'-' => {class => 'bizarro::BOP::subtract', isCommand => 1},
'- ' => {class => 'bizarro::BOP::subtract', isCommand => 1},
' -' => {class => 'bizarro::BOP::subtract', isCommand => 1},
'*' => {class => 'bizarro::BOP::multiply', isCommand => 1},
'* ' => {class => 'bizarro::BOP::multiply', isCommand => 1},
' *' => {class => 'bizarro::BOP::multiply', isCommand => 1});

$flag = 1;
if ($c[0] == $s[1]) { </font></div> <div><font face="courier new, courier, monospace"> $flag = -1;</font></div> <div><font face="courier new, courier, monospace"> foreach my $j (0..1) {</font></div> <div><font face="courier new, courier, monospace"> $score[$j] = 0; </font></div> <div><font face="courier new, courier, monospace"> if ($c[$j]->typeMatch($s[1-$j]) && $c[$j] == $s[1-$j]) { $score[$j] = 1; }
$score[$j+2] = 0;
if ($c[$j+2]->typeMatch($s[1-$j+2]) && $c[$j+2] == $s[1-$j+2]) { $score[$j+2] = 1; }
}
}
else {</font></div> <div><font face="courier new, courier, monospace"> foreach my $j (0..3) {</font></div> <div><font face="courier new, courier, monospace"> $score[$j] = 0; </font></div> <div><font face="courier new, courier, monospace"> if ($c[$j]->typeMatch($s[$j]) && $c[$j] == $s[$j]) { $score[$j] = 1; }
}
}

$student = Formula("$s[4]"); $correct = Formula("$flag*$c[4]")->reduce;
if ($correct != $student) {</font></div> <div><font face="courier new, courier, monospace"> $score[4] = 0;</font></div> <div><font face="courier new, courier, monospace"> }
else {</font></div> <div><font face="courier new, courier, monospace"> Context()->flags->set(bizarroDiv=>1,bizarroSub=>1,bizarroMul=>1); </font></div> <div><font face="courier new, courier, monospace"> delete $correct->{test_values}, $student->{test_values};
# Context()->flags->set(limits=>[0.25,0.4]);
if (($correct != $student) || ($student != $correct)) {</font></div> <div><font face="courier new, courier, monospace"> $self->setMessage(5, "Your Wronskian answer is correct, but please simplify it further");</font></div> <div><font face="courier new, courier, monospace"> $score[4] = 0;</font></div> <div><font face="courier new, courier, monospace"> }
# Value->Error("Your Wronskian answer is correct, but please simplify it further") unless (($correct == $student) or ($student == $correct));
else {</font></div> <div><font face="courier new, courier, monospace"> $score[4] = 1;</font></div> <div><font face="courier new, courier, monospace"> }
Context()->flags->set(bizarroDiv=>0,bizarroSub=>0,bizarroMul=>0);
}

###### Check W1 Determinant contingent on the choices made by student in W above.
$i = 5; # offset
## Check first column is 0, f(x)
$score[$i] = ($c[$i]->typeMatch($s[$i]) && $c[$i] == $s[$i]);
$score[$i+2] = ($c[$i+2]->typeMatch($s[$i+2]) && $c[$i+2] == $s[$i+2]);
## Check second column contingent on student choices made in W above.
$score[$i+1] = ($c[$i+1]->typeMatch($s[$i+1]) && $s[1] == $s[$i+1]);
$score[$i+3] = ($c[$i+3]->typeMatch($s[$i+3]) && $s[3] == $s[$i+3]);
## Check determinant W1
$off = 0;
if ($flag==-1) { $off = 5;}
$student = Formula("$s[$i+4]"); $correct = Formula("$flag*$c[$i+4+$off]")->reduce;
if ($correct != $student) {</font></div> <div><font face="courier new, courier, monospace"> $score[$i+4] = 0;</font></div> <div><font face="courier new, courier, monospace"> }
else {</font></div> <div><font face="courier new, courier, monospace"> Context()->flags->set(bizarroDiv=>1,bizarroMul=>1);</font></div> <div><font face="courier new, courier, monospace"> delete $correct->{test_values}, $student->{test_values};
# Context()->flags->set(limits=>[0.25,0.4]);
if (($correct != $student) || ($student != $correct)) {</font></div> <div><font face="courier new, courier, monospace"> $self->setMessage($i+5, "Your W1 answer is correct, but please simplify the final determinant expression further");</font></div> <div><font face="courier new, courier, monospace"> $score[$i+4] = 0;</font></div> <div><font face="courier new, courier, monospace"> }
# Value->Error("Your Wronskian answer is correct, but please simplify it further") unless (($correct == $student) or ($student == $correct));
else {</font></div> <div><font face="courier new, courier, monospace"> $score[$i+4] = 1;</font></div> <div><font face="courier new, courier, monospace"> }
Context()->flags->set(bizarroDiv=>0,bizarroMul=>0);
}

###### Check W2 Determinant contingent on the choices made by student in W above.
$i = 10; # offset
## Check second column is 0, f(x)
$score[$i+1] = ($c[$i+1]->typeMatch($s[$i+1]) && $c[$i+1] == $s[$i+1]);
$score[$i+3] = ($c[$i+2]->typeMatch($s[$i+2]) && $c[$i+3] == $s[$i+3]);
## Check first column contingent on student choices made in W above.
$score[$i] = ($c[$i]->typeMatch($s[$i]) && $s[0] == $s[$i]);
$score[$i+2] = ($c[$i+2]->typeMatch($s[$i+2]) && $s[2] == $s[$i+2]);
## Check determinant W2

$student = Formula("$s[$i+4]"); $correct = Formula("$flag*$c[$i+4-$off]")->reduce;
if ($correct != $student) {</font></div> <div><font face="courier new, courier, monospace"> $score[$i+4] = 0;</font></div> <div><font face="courier new, courier, monospace"> }
else {</font></div> <div><font face="courier new, courier, monospace"> Context()->flags->set(bizarroDiv=>1,bizarroMul=>1);</font></div> <div><font face="courier new, courier, monospace"> delete $correct->{test_values}, $student->{test_values};
## Context()->flags->set(limits=>[0.25,0.4]);
if (($correct != $student) || ($student != $correct)) {</font></div> <div><font face="courier new, courier, monospace"> $self->setMessage($i+5, "Your W2 answer is correct, but please simplify the final determinant expression further");</font></div> <div><font face="courier new, courier, monospace"> $score[$i+4] = 0;</font></div> <div><font face="courier new, courier, monospace"> }
# Value->Error("Your Wronskian answer is correct, but please simplify it further") unless (($correct == $student) or ($student == $correct));
else {</font></div> <div><font face="courier new, courier, monospace"> $score[$i+4] = 1;</font></div> <div><font face="courier new, courier, monospace"> }
Context()->flags->set(bizarroDiv=>0,bizarroMul=>0);
}

#### Check for u1 prime
$student = Formula("$s[15]");
if ($flag == -1) {</font></div> <div><font face="courier new, courier, monospace"> $correct2 = Formula("$c[15]")->reduce;</font></div> <div><font face="courier new, courier, monospace"> $correct = Formula("$c[16]")->reduce;</font></div> <div><font face="courier new, courier, monospace"> }
else {</font></div> <div><font face="courier new, courier, monospace"> $correct2 = Formula("$c[16]")->reduce;</font></div> <div><font face="courier new, courier, monospace"> $correct = Formula("$c[15]")->reduce;</font></div> <div><font face="courier new, courier, monospace"> }

if ($correct != $student) {</font></div> <div><font face="courier new, courier, monospace"> $score[15] = 0;</font></div> <div><font face="courier new, courier, monospace"> }
else {</font></div> <div><font face="courier new, courier, monospace"> Context()->flags->set(bizarroDiv=>1,bizarroMul=>1);</font></div> <div><font face="courier new, courier, monospace"> delete $correct->{test_values}, $student->{test_values};
## Context()->flags->set(limits=>[0.25,0.4]);
if (($correct != $student) || ($student != $correct)) {</font></div> <div><font face="courier new, courier, monospace"> $self->setMessage(16, "Your u1' is correct, but please simplify the final expression further");</font></div> <div><font face="courier new, courier, monospace"> $score[15] = 0;</font></div> <div><font face="courier new, courier, monospace"> }
# Value->Error("Your Wronskian answer is correct, but please simplify it further") unless (($correct == $student) or ($student == $correct));
else {</font></div> <div><font face="courier new, courier, monospace"> $score[15] = 1;</font></div> <div><font face="courier new, courier, monospace"> }
Context()->flags->set(bizarroDiv=>0,bizarroMul=>0);
}

#### Check for u2 prime
$student = Formula("$s[16]");
if ($correct2 != $student) {</font></div> <div><font face="courier new, courier, monospace"> $score[16] = 0;</font></div> <div><font face="courier new, courier, monospace"> }
else {</font></div> <div><font face="courier new, courier, monospace"> Context()->flags->set(bizarroDiv=>1,bizarroMul=>1);</font></div> <div><font face="courier new, courier, monospace"> delete $correct2->{test_values}, $student->{test_values};
## Context()->flags->set(limits=>[0.25,0.4]);
if (($correct2 != $student) || ($student != $correct2)) {</font></div> <div><font face="courier new, courier, monospace"> $self->setMessage(17, "Your u2' is correct, but please simplify the final expression further");</font></div> <div><font face="courier new, courier, monospace"> $score[16] = 0;</font></div> <div><font face="courier new, courier, monospace"> }
else {</font></div> <div><font face="courier new, courier, monospace"> $score[16] = 1;</font></div> <div><font face="courier new, courier, monospace"> }
Context()->flags->set(bizarroDiv=>0,bizarroMul=>0);
}

#### Check for u1
$student = Formula("$s[17]");
if ($flag == -1) {</font></div> <div><font face="courier new, courier, monospace"> $correct2 = Formula("$c[17]")->reduce;</font></div> <div><font face="courier new, courier, monospace"> $correct = Formula("$c[18]")->reduce;</font></div> <div><font face="courier new, courier, monospace"> }
else {</font></div> <div><font face="courier new, courier, monospace"> $correct2 = Formula("$c[18]")->reduce;</font></div> <div><font face="courier new, courier, monospace"> $correct = Formula("$c[17]")->reduce;</font></div> <div><font face="courier new, courier, monospace"> }
$score[17] = ($student == $correct || $correct == $student);
#### Check for u2
$student = Formula("$s[18]");
$score[18] = ($student == $correct2 || $correct2 == $student);
return [ @score ];
}

);

##################################
# reset the context and get rid of adaptive parameters

Context("Numeric");
Context()->variables->add(
'y' =>'Real','t' =>'Real',
'c1'=>'Real',
'c2'=>'Real',
);
Context()->variables->remove('x');
Context()->variables->set(
'c1'=>{limits=>[2,4]},
'c2'=>{limits=>[2,4]},
'y'=>{limits=>[-2,2]},
't'=>{limits=>[-2,2]}
);

$yhomogeneous = Compute("c1 e^($r t) + c2 t e^($r t)");

Context()->texStrings;
BEGIN_TEXT
Use variation of parameters to find a particular solution to:
\(\quad \displaystyle {y'' + $a y' + $b y = \frac{$c e^{$r t}}{t^2+1}} \).

\{ BeginList('OL',type=>'a') \}
$ITEM Find the most general solution to the
associated homogeneous differential equation.
Use \( c_1 \) and \( c_2 \) in your answer to denote arbitrary constants. $BR
Enter \( c_1 \) as ${BTT}c1${ETT} and \( c_2 \) as ${BTT}c2${ETT}.
$BR
$BR
\( y_c = \)
\{ ans_rule(60) \}
$ITEMSEP
$ITEM Use the two independent solutions of the homogeneous form of the DE to enter the Wronskian determinant, \(W\):

$PAR
$BCENTER
\{ </font></div> <div><font face="courier new, courier, monospace">mbox(</font></div> <div><font face="courier new, courier, monospace"> "\(W = \mathrm{det} \)",
display_matrix([
[$multians1->ans_rule(20),$multians1->ans_rule(20)],
[$multians1->ans_rule(20),$multians1->ans_rule(20)]], align=>'cc'),
" = ".$SPACE.$multians1->ans_rule(30)
);
\}
$ECENTER
$ITEMSEP
$ITEM Now enter the determinants, \(W_1\) and \(W_2\):

$PAR
$BCENTER
\{ </font></div> <div><font face="courier new, courier, monospace">mbox(</font></div> <div><font face="courier new, courier, monospace"> "\(W_1 = \mathrm{det} \)",
display_matrix([
[$multians1->ans_rule(20),$multians1->ans_rule(20)],
[$multians1->ans_rule(20),$multians1->ans_rule(20)]], align=>'cc'),
" = ".$SPACE.$multians1->ans_rule(30)
);
\}
$ECENTER
$PAR
$BCENTER
\{ </font></div> <div><font face="courier new, courier, monospace">mbox(</font></div> <div><font face="courier new, courier, monospace"> "\(W_2 = \mathrm{det} \)",
display_matrix([
[$multians1->ans_rule(20),$multians1->ans_rule(20)],
[$multians1->ans_rule(20),$multians1->ans_rule(20)]], align=>'cc'),
" = ".$SPACE.$multians1->ans_rule(30)
);
\}
$ECENTER
$ITEMSEP
$ITEM Use these results to determine \(u_1^{\prime}\) and \(u_2^\prime\). (Please simplify them. This will make it easier to integrate in the next step.)
$PAR
\(u_1^\prime = \frac{W_1}{W} =\) \{$multians1->ans_rule(30) \}
$PAR
\(u_2^\prime = \frac{W_2}{W} =\) \{$multians1->ans_rule(30) \}
$ITEMSEP
$ITEM Now integrate \(u_1^{\prime}\) to determine \(u_1\),
$PAR
\(u_1 = \int{u_1^\prime\,dt} =\) \{$multians1->ans_rule(30) \} \( + \quad C_1\)
$PAR
and integrate \(u_2^{\prime}\) to determine \(u_2\).
$PAR
\(u_2 = \int{u_2^\prime\,dt} =\) \{$multians1->ans_rule(30) \} \( + \quad C_2\)
$ITEMSEP
$ITEM Finally, enter the simplest form of the particular solution you obtained (not including any terms that are part of the complementary solution to the homogeneous form of this DE).
$PAR
\(y_{p} = \) \{ans_rule(60)\}

\{ EndList('OL') \}
END_TEXT
Context()->normalStrings;

ANS( $yhomogeneous->cmp(
checker => sub {</font></div> <div><font face="courier new, courier, monospace"> my ( $correct, $student, $answerHash ) = @_;</font></div> <div><font face="courier new, courier, monospace"> my $stu = Formula($student);</font></div> <div><font face="courier new, courier, monospace"><br /></font></div> <div><font face="courier new, courier, monospace"> ################################</font></div> <div><font face="courier new, courier, monospace"> # Check for arbitrary constants</font></div> <div><font face="courier new, courier, monospace"> #</font></div> <div><font face="courier new, courier, monospace"> Value->Error("Is your answer the most general solution?") </font></div> <div><font face="courier new, courier, monospace"> if ( </font></div> <div><font face="courier new, courier, monospace"> Formula($stu->D('c1'))==Formula(0) || </font></div> <div><font face="courier new, courier, monospace"> Formula($stu->D('c2'))==Formula(0) </font></div> <div><font face="courier new, courier, monospace"> );</font></div> <div><font face="courier new, courier, monospace"><br /></font></div> <div><font face="courier new, courier, monospace"> ############################################</font></div> <div><font face="courier new, courier, monospace"> # Check for linear independence (Wronskian)</font></div> <div><font face="courier new, courier, monospace"> #</font></div> <div><font face="courier new, courier, monospace"> my $t = Real(1.24);</font></div> <div><font face="courier new, courier, monospace"><br /></font></div> <div><font face="courier new, courier, monospace"> my $a11 = $stu->eval('c1'=>1,'c2'=>0,t=>$t,y=>0);</font></div> <div><font face="courier new, courier, monospace"> my $a12 = $stu->eval('c1'=>0,'c2'=>1,t=>$t,y=>0);</font></div> <div><font face="courier new, courier, monospace"> </font></div> <div><font face="courier new, courier, monospace"> my $a21 = $stu->D('t')->eval('c1'=>1,'c2'=>0,t=>$t,y=>0);</font></div> <div><font face="courier new, courier, monospace"> my $a22 = $stu->D('t')->eval('c1'=>0,'c2'=>1,t=>$t,y=>0);</font></div> <div><font face="courier new, courier, monospace"><br /></font></div> <div><font face="courier new, courier, monospace"> # my $wronskian = $a11*$a22 - $a21*$a12;</font></div> <div><font face="courier new, courier, monospace"> # Value->Error("Your functions are not linearly independent or your answer is not complete") </font></div> <div><font face="courier new, courier, monospace"> # if ($wronskian==Real(0));</font></div> <div><font face="courier new, courier, monospace"><br /></font></div> <div><font face="courier new, courier, monospace"> Value->Error("Your functions are not linearly independent or your answer is not complete") </font></div> <div><font face="courier new, courier, monospace"> if ($a11 * $a22 == $a21 * $a12);</font></div> <div><font face="courier new, courier, monospace"><br /></font></div> <div><font face="courier new, courier, monospace"> ########################################################</font></div> <div><font face="courier new, courier, monospace"> # Check that the student answer is a solution to the DE</font></div> <div><font face="courier new, courier, monospace"> #</font></div> <div><font face="courier new, courier, monospace"> my $stu1 = Formula($stu->D('t'));</font></div> <div><font face="courier new, courier, monospace"> my $stu2 = Formula($stu->D('t','t'));</font></div> <div><font face="courier new, courier, monospace"> return (($stu2 + $a*$stu1) == (-1 * $b * $stu));</font></div> <div><font face="courier new, courier, monospace">}));

ANS( $multians1->cmp());

ANS( $yp->cmp() );

ENDDOCUMENT() ;

Please let me know if you have any ideas about where my issue may be.

Thanks!

Paul
In reply to Paul Seeburger

Re: Can't generate enough valid points for comparison error

by Paul Seeburger -
Ok, I found the error in another post from a year ago. I guess there is something to using the exact phrase option in the search on the forums!

In a reply from Alex Jordan to Bruce Yoshiwara, Alex explained that now the definitions of the bizarro arithmetic options need to be on the context BEFORE any objects are created.

It's interesting how this did not used to cause a problem, but it's great to get this figured out!! I am sure it will prove helpful in many other problems too.


Paul