Question:
This project is a continuation of the previous project. For a quadratic expression such as
a
x
2
+
b
x
+
c
ax^2+bx+c
ax2+bx+c, a real root is any double number
x
x
x such that
a
x
2
+
b
x
+
c
=
0
ax^2+bx+c=0
ax2+bx+c=0. For example, the quadratic expression
2
x
2
+
8
x
+
6
2x^2+8x+6
2x2+8x+6 has one of its real roots at
x
=
−
3
x=-3
x=−3, because substituting
x
=
−
3
x=-3
x=−3 in the formula
2
x
2
+
8
x
+
6
2x^2+8x+6
2x2+8x+6 yields the value:
2
×
(
−
3
2
)
+
8
×
(
−
3
)
+
6
=
0
2\times(-3^2)+8\times(-3)+6=0
2×(−32)+8×(−3)+6=0There are six rules for finding the real roots of a quadratic expression:
(1) If
a
a
a,
b
b
b, and
c
c
c are all zero, then every value of
x
x
x is a real root.
(2) If
a
a
a and
b
b
b are zero, but
c
c
c is nonzero, then there are no real roots.
(3) If
a
a
a is zero, and b is nonzero, then the only real root is
x
=
−
c
/
b
x=-c/b
x=−c/b.
(4) If
a
a
a is nonzero and
b
2
<
4
a
c
b^2<4ac
b2<4ac, then there are no real roots.
(5) If
a
a
a is nonzero and
b
2
=
4
a
c
b^2=4ac
b2=4ac, then there is one real root
x
=
−
b
/
2
a
x=-b/2a
x=−b/2a.
(6) If
a
a
a is nonzero and
b
2
>
4
a
c
b^2>4ac
b2>4ac, then there are two real roots:
x
=
−
b
−
b
2
−
4
a
c
2
a
x=\frac{-b-\sqrt{b^2-4ac}}{2a}
x=2a−b−b2−4ac
x
=
−
b
+
b
2
−
4
a
c
2
a
x=\frac{-b+\sqrt{b^2-4ac}}{2a}
x=2a−b+b2−4acWrite a new member function that returns the number of real roots of a quadratic expression. This answer could be 0, or 1, or 2, or infinity. In the case of an infinite number of real roots, have the member function return 3. (Yes, we know that 3 is not infinity, but for this purpose it is close enough!) Write two other member functions that calculate and return the real roots of a quadratic expression. The precondition for both function is that the expression has at least one real root. If there are two real roots, then one of the functions returns the smaller of the two roots, and the other function returns the larger of the two roots. If every value of
x
x
x is a real root, then both function should return zero.
My answer:
quadratic.h
#ifndef QUADRATIC_H
#define QUADRATIC_H
class quadratic{
public:
quadratic(){
a = b = c = 0;
};
void set_coefficients(double m, double n, double q);
double get_a() const;
double get_b() const;
double get_c() const;
double evaluate_exp(double x);
int root_num();
double root1();
double root2();
private:
double a, b, c;
};
quadratic operator +(const quadratic& q1, const quadratic& q2);
quadratic operator *(double r, const quadratic& q);
#endif
quadratic.cpp
#include "quadratic.h"
#include <cmath>
#include <assert.h>
#include <iostream>
void quadratic::set_coefficients(double m, double n, double q){
a = m;
b = n;
c = q;
}
double quadratic::get_a() const{
return a;
}
double quadratic::get_b() const{
return b;
}
double quadratic::get_c() const{
return c;
}
double quadratic::evaluate_exp(double x){
return a * pow(x, 2) + b * x + c;
}
int quadratic::root_num(){
if(!(a || b || c))
return 3;// stands for infinity
if(a == 0 && b == 0 && c!=0)
return 0;
if(a == 0 && b !=0)
return 1;
if(a != 0 && pow(b, 2) < 4*a*c)
return 0;
if(a != 0 && pow(b, 2) == 4*a*c)
return 1;
if(a != 0 && pow(b, 2) > 4*a*c)
return 2;
return -1;
}
double quadratic::root1(){
assert(root_num() != 0);
if(root_num() == 1 && a == 0)
return -c/b;
if(root_num() == 1 && a != 0)
return -b/(2*a);
if(root_num() == 2)
return (-b - pow((b*b - 4*a*c), 0.5))/(2*a);
return -1;
}
double quadratic::root2(){
assert(root_num() != 0);
if(root_num() == 1 && a == 0)
return -c/b;
if(root_num() == 1 && a != 0)
return -b/(2*a);
if(root_num() == 2)
return (-b + pow((b*b - 4*a*c), 0.5))/(2*a);
return -1;
}
quadratic operator +(const quadratic& q1, const quadratic& q2){
quadratic q3;
q3.set_coefficients(q1.get_a() + q2.get_a(), q1.get_b() + q2.get_b(), q1.get_c() + q2.get_c());
return q3;
}
quadratic operator *(double r, const quadratic& q){
quadratic q1;
q1.set_coefficients(r * q.get_a(), r * q.get_b(), r * q.get_c());
return q1;
}
main.cpp
#include <iostream>
#include "quadratic.h"
void quadratic_info(quadratic);
void quadratic_roots(quadratic);
int main(){
quadratic a;
a.set_coefficients(1, 2, 1);
quadratic_info(a);
std::cout << "when x = 3, gets " << a.evaluate_exp(3) << std::endl;
quadratic_roots(a);
quadratic b;
b.set_coefficients(0, 3, -1);
quadratic_info(b);
std::cout << "when x = 3, gets " << b.evaluate_exp(3) << std::endl;
quadratic_roots(b);
quadratic c;
c = a + b;
quadratic_info(c);
std::cout << "when x = 6, gets " << c.evaluate_exp(6) << std::endl;
quadratic_roots(c);
c = 3 * c;
quadratic_info(c);
std::cout << "when x = -2, gets " << c.evaluate_exp(-2) << std::endl;
quadratic_roots(c);
quadratic d;
d.set_coefficients(0, 0, -1);
quadratic_info(d);
std::cout << "when x = 3, gets " << d.evaluate_exp(3) << std::endl;
quadratic_roots(d);
quadratic e;
e.set_coefficients(0, 0, 0);
quadratic_info(e);
std::cout << "when x = 3, gets " << e.evaluate_exp(3) << std::endl;
quadratic_roots(e);
return 0;
}
void quadratic_info(quadratic a){
std::cout << "quadratic info:" << std::endl;
std::cout << "a = " << a.get_a() << ", b = " << a.get_b() << ", c = " << a.get_c() << "." << std::endl;
}
void quadratic_roots(quadratic a){
switch(a.root_num()){
case 0:
std::cout << "This quadratic has no roots at all." << std::endl;
break;
case 1:
std::cout << "This quadratic has only one root and it is " << a.root1() << "." << std::endl;
break;
case 2:
std::cout << "This quadratic has two roots and they are " << a.root1() << " and " << a.root2() << "." << std::endl;
break;
case 3:
std::cout << "This quadratic has infinite roots." << std::endl;
break;
default:
std::cout << "Unexpected error!" << std::endl;
}
}
结果:
Reference:
整理自 Data Structures and Other Objects Using C++ ( Fourth Edition ) Michael Main, Walter Savitch. p121