一、根的初始值的确定
首先最简单的方法莫过于画一个函数图像看一看。
其次,我们可以使用如下两个原则去确定初始根
<1>、y(k-1)y(k)<0,该点的左右两边y值正负号相反,由中值定理知道必有一根。
<2>、|y(k)|<一个小数&&(y(k)-y(k-1))(y(k+1)-y(k))<0;这表示y(k)足够小,且曲线的斜率在该点附近改变正负号
我们以以下这道例题为说明
例题
【问题描述】在[a,b]区间内寻找方程x5-2*x-1=0的根的初始近似值位置,确定不动点迭代的初始点(可能有多个),然后使用不动点迭代法求方程的根(可能有多个根)。前后两次迭代的差的绝对值小于delta后停止迭代。
【输入形式】在屏幕上输入3个数,依次为区间左端点值a、右端点值b和所求根的精度值。各数间都以一个空格分隔。根据输入的所求根的精度值可求得delta。测试用例的输入满足:b>a, 1<=d<=8, d为正整数。
【输出形式】每一行输出一个根,保留d位小数。根据a、b的值,可能荐在0或1或多个根。若在区间[a, b]内没有根,则输出error。
【样例1输入】
-1.2 1.5 3
【样例1输出】
-1.000
-0.519
1.291
【样例1说明】输入:左端点a值为-1.2,右端点b值为1.5,前后两次迭代的差的绝对值小于delta=10(-3)后停止迭代。输出:从小到大顺序输出三个根的值,保留3位小数。
它的求初始值代码如下:
double a, b, n;
#define vi vector<double>
vi approot(double x, double epsilon)
{
auto f = [&](double x) -> double {
return pow(x, 5.0) - 2 * x - 1;
};
vi res;
double y = f(x);
double ma = y, mi = y;
for (double i = a; i <= b; i += epsilon)
ma = max(ma, f(i)), mi = min(mi, f(i));
double eps = (ma - mi) * epsilon;
for (double i = a + epsilon; i <= b - epsilon; i += epsilon)
{
if (f(i) * f(i - epsilon) <= 0)
res.emplace_back((2 * i + epsilon) / 2);
double s = (f(i) - f(i - epsilon)) * (f(i + epsilon) - f(i));
if (fabs(f(s)