Вычисление интеграла методом левых прямоугольников
Public static double rectangle(int x1[],double f[],int n) {
double n1=n;
double h=(n1-1)/n1;
double Integral=0.0;
for(int i=0;i<=n-1;i++) {
Integral+=h*(f[i]);
}
System.out.println(Integral);
return Integral;
}
public void static main(String[] args) {
int a=0,b=4;
int n=b-a+1;
int x1[]=new int[n];
double f[]=new double[n];
String format = "|%1$-16s|%2$-16s|\n";
System.out.format(format, "----------------", "----------------");
System.out.format(format, " y(x) ", " x ");
System.out.format(format, "----------------", "----------------");
int k=0;
for (int x = a; x <= b;x++) {
System.out.format("|%15.7e |%15d |%n",Math.pow(Math.E, x)-x*x*x,x);
System.out.format(format, "----------------", "----------------");
x1[k] = x;
f[k] = Math.pow(Math.E, x) - x * x * x;
if(k<=b-1) k += 1;
}
rectangle(x1,f,n);
}
Сделал вычисление интеграла методом левых прямоугольников. Значение отличается от значений интеграла в калькуляторе где-то на 1-1,5.Таблицу вывести и заполнить массивы требовалось по условию. Я точно правильно описал алгоритм? А то может из-за какой-то ошибки возникает такая большая погрешность. Допустим, на отрезке [0;4] калькулятор из интернета выдает −10.40184996685576,а у меня -11.36718009302273. На отрезке [0;5] вместо −8.836840897423393 выводит 7.670153321915132.
Ответы (1 шт):
Во-первых, ты считаешь по методу левых треугольников, поэтому тебе не нужно высчитывать интеграл правой границы (<= b -> < b).
Во-вторых, так значение h не считается, h = (правая_гр - левая_гр) / кол-во_отрезков, в данном случае (4-0) / 4 = 1, а не (4-1) / 4.
Отсюда видны закономерности, а также график, который наглядно показывает, почему погрешность больше, чем даже предполагал это ты.
С применением предложенных изменений ответом будет ~-4.8.
К стилю кода есть множество вопросов - это и нарушения в области отступов, и бесполезные переменные, и функция с непредсказуемым (по названию) функционалом. Я бы переписал это так:
public static double getIntegralValueByLeftRectangle(double funcValues[], int from, int to) {
int intervalsCount = funcValues.length; // кол-во интервалов можно определить из кол-ва переданных значений ф-ции
double h = getIntervalLength(from, to, intervalsCount);
double integral = 0;
for(int i = 0; i < intervalsCount; i++) {
integral += h * funcValues[i];
}
return integral;
}
public static void main(String[] args) {
int from = 0, to = 4, intervalsCount = 4;
double intervalLength = getIntervalLength(from, to, intervalsCount);
double funcValues[] = new double[intervalsCount];
String format = "|%1$-16s|%2$-16s|\n";
System.out.format(format, "----------------", "----------------");
System.out.format(format, " y(x) ", " x ");
System.out.format(format, "----------------", "----------------");
double leftX = from;
for (int i = 0; i < intervalsCount; i++, leftX += intervalLength) {
System.out.format("|%15.7e |%15.2f |%n", Math.pow(Math.E, leftX) - leftX * leftX * leftX, leftX); // 15d -> 15.2f
System.out.format(format, "----------------", "----------------");
funcValues[i] = Math.pow(Math.E, leftX) - leftX * leftX * leftX;
}
System.out.println(getIntegralValueByLeftRectangle(funcValues, from, to));
}
public static double getIntervalLength(double from, double to, int intervalsCount) {
return (to - from) / intervalsCount;
}
Вывод:
|----------------|----------------|
| y(x) | x |
|----------------|----------------|
| 1.0000000e+00 | 0 |
|----------------|----------------|
| 1.7182818e+00 | 1 |
|----------------|----------------|
| -6.1094390e-01 | 2 |
|----------------|----------------|
| -6.9144631e+00 | 3 |
|----------------|----------------|
-4.807125149422641
