Integration by substitution: general partial credit checks and problem templates.
Jump to navigation
Jump to search
The following problem will show you how to check when the student answer S and the correct answer C are in the relationship S = aC+b for any real a and b. It is also designed as a problem template. This means that you can obtain many different problems spending a few seconds and modifying a few lines. One needs to be a little careful when modifying code. Go through the exercises for more details on this.
# Created by Nikola Kuzmanovski ######################################################################## DOCUMENT(); loadMacros( "PGstandard.pl", "MathObjects.pl", "PGinfo.pl", ); TEXT(beginproblem()); $showPartialCorrectAnswers = 1; ############################################################## # # Setup # # Context("Numeric"); Context()->variables->add(u => "Real"); Context()->variables->add(X => "Real"); $f = Formula("e^x"); $F = Formula("e^x"); $g = Formula("sin(x)"); $gD = $g->D('x'); $integrand = $f->substitute(x => $g) * $gD; $integral = $F->substitute(x => $g); $fu = $f->substitute(x => "u"); $Fu = $F->substitute(x => "u"); $lowerLimit = random(10, 19, 1); $upperLimit = random(20, 29, 1); $area = $integral->eval(x => $upperLimit) - $integral->eval(x => $lowerLimit); ############################################################## # # Text # # Context()->texStrings; BEGIN_TEXT This problem deals with the following integral \[ \int $integrand dx .\] Your job is to evaluate it using substitution. We are going to use the variable \(u\) as the substitution variable. Give a choice for \(u\) below. $BR $BCENTER \(\displaystyle u = \) \{ans_rule\}. $ECENTER $BR Then $BCENTER \(\displaystyle du = \) \{ans_rule\} \(dx\). $ECENTER $BR With this we can change the integral \(\displaystyle \int $integrand dx \) to an integral of the form \(\displaystyle \int g(u) du\) for some function \(g(u)\). Input this function in the line below $BBOLD (note that the \(du\) is included at the end, so you don't need to input it). $EBOLD. $BR $BCENTER \(\displaystyle \int $integrand dx = \int \) \{ans_rule\} \(du\). $ECENTER $BR Next, find the general antiderivative $BBOLD (note that the \(+C\) is included at the end, so you don't need to input it). $EBOLD $BR $BCENTER \(\displaystyle \int $integrand dx = \) \{ans_rule\} \(+C\). $ECENTER $BR Finally, compute $BR $BCENTER \(\displaystyle \int_{$lowerLimit}^{$upperLimit} $integrand dx = \) \{ans_rule\}. $ECENTER END_TEXT Context()->normalStrings; ############################################################## # # Answers # # sub checkMult{ my ( $correct, $student ) = @_; if($student->isConstant){ return 0 } my $context = Context()->copy; return 0 if $student == 0; $context->flags->set(no_parameters=>0); $context->variables->add('C0'=>'Parameter'); my $c0 = Formula($context,'C0'); $student = Formula($context,$student); $correct = Formula($context,"$c0 * $correct"); return $correct == $student; } sub checkAdd{ my ( $correct, $student ) = @_; if($student->isConstant){ return 0 } my $context = Context()->copy; return 0 if $student == 0; $context->flags->set(no_parameters=>0); $context->variables->add('C0'=>'Parameter'); my $c0 = Formula($context,'C0'); $student = Formula($context,$student); $correct = Formula($context,"$c0 + $correct"); return $correct == $student; } sub checkMultAdd{ my ( $correct, $student ) = @_; if($student->isConstant){ return 0 } my $context = Context()->copy; return 0 if $student == 0; $context->flags->set(no_parameters=>0); $context->variables->add('C0'=>'Parameter'); $context->variables->add('C1'=>'Parameter'); my $c0 = Formula($context,'C0'); my $c1 = Formula($context,'C1'); $student = Formula($context,$student); $correct = Formula($context,"$c1 + $c0 * $correct"); return $correct == $student; } $studentU = Formula(""); $scoreU = 0.0; $checkU = sub{ if($inputs_ref->{previewAnswers}){ return 0.0; } my ($correctAns, $studentAns, $ansHash) = @_; my $score = 0.0; $studentAns = Formula("$studentAns"); $studentAns = $studentAns->substitute(X => "x"); $studentU = $studentAns; my $studentSub = $f->substitute(x => $studentAns) * $gD; if($integrand == $studentSub){ $ansHash->{ans_message} = "This substitution will work!"; $score = 1.0; }elsif(checkMult($integrand, $studentSub)){ $ansHash->{ans_message} = "This substitution will almost work. The final antiderivative will have an extra multiplicative constant"; $score = 0.9; }elsif(checkMult($correctAns, $studentAns)){ $ansHash->{ans_message} = "Your answer is close to the correct one. You have an extra multiplicative constant."; $score = 0.8; }elsif(checkAdd($correctAns, $studentAns)){ $ansHash->{ans_message} = "Your answer is close to the correct one. You have added an extra constant."; $score = 0.8; }elsif(checkMultAdd($correctAns, $studentAns)){ $ansHash->{ans_message} = "Your answer is close to the correct one. You have added an extra constant and you have an extra multiplicative constant."; $score = 0.7; }else{ $ansHash->{ans_message} = "Your answer won't work. Try reviewing the section on integration by substitution."; } $scoreU = $score; return $score; }; ANS($g->cmp(checker => $checkU)); $studentDiv = Formula(""); $scoreDiv = 0.0; $checkDiv = sub{ if($inputs_ref->{previewAnswers}){ return 0.0; } my ($correctAns, $studentAns, $ansHash) = @_; my $score = 0.0; $studentAns = Formula("$studentAns"); $studentAns = $studentAns->substitute(X => "x"); $studentDiv = $studentAns; if($studentU == Formula("")){ $ansHash->{ans_message} = "This answer depends on the previous answer. You don't get any points for it because you didn't enter anything for the previous answer."; return $score; } my $studentDerivative = $studentU->D('x'); if($studentDerivative == $studentAns){ $ansHash->{ans_message} = "You differentiated correctly!"; $score = 1.0; }elsif(checkAdd($studentDerivative, $studentAns)){ $ansHash->{ans_message} = "It seems like you made some mistake while differentiating. You have some extra additive constant."; $score = 0.9; }elsif(checkMult($studentDerivative, $studentAns)){ $ansHash->{ans_message} = "It seems like you made some mistake while differentiating. You have some extra multiplicative constant."; $score = 0.9; }elsif(checkMultAdd($studentDerivative, $studentAns)){ $ansHash->{ans_message} = "It seems like you made some mistake while differentiating. You have some extra additive constant and an extra multiplicative constant."; $score = 0.8; }else{ $ansHash->{ans_message} = "It seems that you didn't differentiate correctly. Try reviewing differentiation from Calculus I."; } return $score; }; ANS($gD->cmp(checker => $checkDiv)); $studentSub = Formula(""); $scoreSub = 0.0; $checkSub = sub{ if($inputs_ref->{previewAnswers}){ return 0.0; } my ($correctAns, $studentAns, $ansHash) = @_; my $score = 0.0; $studentAns = Formula("$studentAns"); $studentSub = $studentAns; if($studentU == Formula("") || $studentDiv == Formula("")){ $ansHash->{ans_message} = "This answer depends on the previous two answers. You don't get any points for it because you didn't enter anything for the previous answers."; return $score; } if($correctAns == $studentAns){ $ansHash->{ans_message} = "Good work substituting!"; $score = 1.0; }elsif(checkAdd($correctAns, $studentAns)){ $ansHash->{ans_message} = "It seems like you made some mistake while substituting. You have some extra additive constant."; $score = 0.9; }elsif(checkMult($correctAns, $studentAns)){ $ansHash->{ans_message} = "It seems like you made some mistake while substituting. You have some extra multiplicative constant."; $score = 0.9; }elsif(checkMultAdd($correctAns, $studentAns)){ $ansHash->{ans_message} = "It seems like you made some mistake while substituting. You have some extra additive constant and an extra multiplicative constant."; $score = 0.8; }else{ $ansHash->{ans_message} = "It seems that your answer is not correct. Try reviewing integration by substitution."; } return $score; }; ANS($fu->cmp(checker => $checkSub)); $studentIntegral = Formula(""); $scoreIntegral = 0.0; $checkIntegral = sub{ if($inputs_ref->{previewAnswers}){ return 0.0; } my ($correctAns, $studentAns, $ansHash) = @_; my $score = 0.0; $studentAns = Formula("$studentAns"); $studentAns = $studentAns->substitute(X => "x"); $studentIntegral = $studentAns; if(checkAdd($correctAns, $studentAns)){ $ansHash->{ans_message} = "Great Job!"; $score = 1.0; }elsif(checkMultAdd($correctAns, $studentAns)){ $ansHash->{ans_message} = "It seems like you made some mistake while integrating. You have some extra multiplicative constant."; $score = 0.9; }elsif(checkAdd($Fu, $studentAns)){ $ansHash->{ans_message} = "You forgot to switch the u at the end."; $score = 0.8; }elsif(checkMultAdd($Fu, $studentAns)){ $ansHash->{ans_message} = "You forgot to switch the u at the end and you have an extra multiplicative constant."; $score = 0.7; }else{ $ansHash->{ans_message} = "It seems that your answer is not correct. Try reviewing integration by substitution."; } $scoreIntegral = $score; return $score; }; ANS($integral->cmp(checker => $checkIntegral)); $studentFTC = Formula(""); $scoreFTC = 0.0; $checkFTC = sub { if($inputs_ref->{previewAnswers}){ return 0.0; } my ($correctAns, $studentAns, $ansHash) = @_; my $score = 0.0; $studentAns = Formula("$studentAns"); $studentIntegral = $studentIntegral->substitute(u => "x"); if($studentU == Formula("") || $studentDiv == Formula("") || $studentSub == Formula("")){ $ansHash->{ans_message} = "This answer depends on the previous three answers. You don't get any points for it because you didn't enter anything for the previous answers."; $scoreFTC = 0.0; return $score; } if($scoreIntegral == 1.0 && $correctAns == $studentAns){ $score = 1.0; $scoreFTC = $score; $ansHash->{ans_message} = "You computed the antiderivative correctly and used the Fundamental Theorem of Calculus correctly!"; return $score; } eval{ my $lowerEval = $studentIntegral->eval(x => $lowerLimit); my $upperEval = $studentIntegral->eval(x => $upperLimit); if ($upperEval - $lowerEval == $studentAns || $correctAns == $studentAns){ $ansHash->{ans_message} = "You didn't compute the antiderivative correctly. However, you used the Fundamental Theorem of Calculus correctly."; $score = 1.0; }elsif($lowerEval - $upperEval == $studentAns){ $ansHash->{ans_message} = "You switched the bounds of integration."; $score = 0.9; }elsif($upperEval + $lowerEval == $studentAns){ $ansHash->{ans_message} = "You need to subtract the lower bound, not add it."; $score = 0.9; }else{ $ansHash->{ans_message} = "It seems that your answer is not correct. Try reviewing the Fundamental Theorem of Calculus."; } 1; } or do{ $ansHash->{ans_message} = "It seems that the answer you gave for the antiderivative doesn't evaluate at the bounds of the definite integral"; $ansHash->{ans_message} = $ansHash->{ans_message} . " Try double checking your work for the antiderivative."; $ansHash->{ans_message} = $ansHash->{ans_message} . " Check for things like division by 0 or negatives under a square root."; }; return $score; }; ANS($area->cmp(checker => $checkFTC)); ENDDOCUMENT();
Exercises:
- Create another problem by modifying $f, $F and $g.
- Create a problem that will produce an error. Think about $area and the last part of the problem.
- Break the isConstant property in checkMult. Write x/x for the first answer.
- Write your own isConstant function that won't have this issue. Think about how variables and the Formula object are implemented. Think about how this affects things like the differentiation operation.