2014-01-26 2 views
0

По существу мое значение дельта дает мне некоторые проблемы, когда я печатаю все переменные в окне консоли, все правильно и правильно, за исключением дельта, значение которого продолжает отображаться как NaN. Почему я не могу понять, почему. Я начинаю учебу в университете в университете, и это действительно дает мне головную боль.Мое значение продолжает отображаться как NaN

import java.util.Scanner; 


public class ReimannSumCalculator { 
    static double a,b,c,start,end; 
    static double partitions; 
    static double delta=end - start/partitions; 

    private static double Quadratic(double a,double b,double c,double x) { 
     double Quadratic = a*x*x + b*x + c; 
     return Quadratic; 
    } 


    public static void leftReiman(double a,double b,double c,double delta,double start,double end) { 
     double leftReiman = 0; 

     for(double x = start; x<end; x+=delta) { 
      leftReiman = delta * Quadratic(a,b,c,x) + leftReiman; 
     } 

     System.out.println("Your left Reiman sum is " + leftReiman); 
    } 

    public static void rightReiman(double a,double b,double c,double delta,double start,double end) { 
     double rightReiman = 0; 

     for(double x = start+delta; x<=end; x+=delta) { 
      rightReiman = delta* Quadratic(a,b,c,x) + rightReiman; 
     } 

     System.out.println("Your right Reiman sum is " + rightReiman); 
    } 

    public static void main(String[] args) { 
     Scanner keyboard = new Scanner(System.in); 

     System.out.println("Please enter some values for a b and c."); 

     a = keyboard.nextDouble(); 
     b = keyboard.nextDouble(); 
     c = keyboard.nextDouble(); 

     System.out.println("Please enter a start and end point."); 

     start = keyboard.nextDouble(); 
     end = keyboard.nextDouble(); 

     System.out.println("Now enter the amount of partitions."); 

     partitions = keyboard.nextInt(); 

     leftReiman(a,b,c,start,end,delta); 
     rightReiman(a,b,c,start,end,delta); 

     System.out.println("The delta is: " + delta); 
     System.out.println("The amount of partitions are: " + partitions); 
     System.out.println("a is: "+ a); 
     System.out.println("b is: "+ b); 
     System.out.println("c is: " + c); 
     System.out.println("The start is: " + start); 
     System.out.println("The end is: " + end); 
    } 
} 
+0

Если вы собираетесь опубликовать какой-либо код, то потребуется некоторое время, чтобы отформатировать его в читаемой форме. На этот раз я сделал это для вас. –

ответ

4

Вы выполняете команду start/partitions, прежде чем инициализировать одну из этих переменных.

Итак, вы по существу вычисляете 0.0/0.0, что равно NaN.

3

Java не превосходит. Он не вычисляет порядок операций для символического выражения автоматически или не пересчитывает выражения при изменении ввода.

Бремя получения порядка операций справа и пересчет значений при их устаревании на программнике.

static double a,b,c,start,end; 

static double partitions; 

static double delta=end - start/partitions; 

эквивалентно

static double a,b,c,start = 0.0d, end = 0.0d; 

static double partitions = 0.0d; 

static double delta=end - start/partitions; 

, потому что все поля принимают нулевое значение для их типа, что эквивалентно

static double a,b,c,start = 0.0d, end = 0.0d; 

static double partitions = 0.0d; 

static double delta=0.0d - 0.0d/0.0d; // division by zero -> NaN 

, потому что поля инициализируются в порядке их объявления ,

Тогда вы не пересчитывать delta в теле main, так что вы в конечном итоге прохождение delta Нан к leftReimann и rightReimann.


Это может иметь смысл использовать целочисленный цикл, чтобы убедиться, что вы имеете дело с правильным количеством разделов вместо сравнения double x двойных границ. Операции с плавающей запятой являются потерями, поэтому вы можете столкнуться с граничными условиями при проверке double s в вашем состоянии цикла.

public static double leftReimann(double a,double b,double c,int partitions,double start,double end) { 
    assert partitions > 0; 

    double leftReimann = 0; 

    double delta = (end - start)/partitions; 

    for(int i = 0; i < partitions; ++i) { 
     double x = start + delta * i; 
     leftReimann += delta * Quadratic(a,b,c,x); 
    } 

    System.out.println("Your left Reimann sum is " + leftReimann); 
    return leftReimann; 
} 

public static double rightReimann(double a,double b,double c,int partitions,double start,double end) { 
    assert partitions > 0; 

    double rightReimann = 0; 

    double delta = (start - end)/partitions; // negative 

    for(int i = 0; i < partitions; ++i) { 
     double x = end + delta * i; 
     rightReimann += delta * Quadratic(a,b,c,x); 
    } 

    System.out.println("Your right Reimann sum is " + rightReimann); 
    return rightReimann; 
} 
+0

+1 для Java не Excel :) –

+0

Спасибо за очень хороший ответ. В этом есть смысл. Я установил значение своей дельта, переучивая его в моем основном методе, однако, есть ли у вас какое-либо представление о том, почему оба метода метода Right и Left Reimann возвращают нуль? –

+0

@JustinTaylor, когда вы его комментируете, что такое 'partitions'? Если разделы малы, вы можете столкнуться с проблемами границ.'<=' по значениям с плавающей запятой является изворотливым, поэтому ваш reimann может быть более надежным, если вы будете рассматривать раздел как 'int' и loop вместо числа разделов. –

0

Там же два варианта, либо сделать дельту функцию

private double getDelta() { return (end - start)/partitions; 

или, вы можете пересчитать дельту после установки конца, начало, или перегородки. (В данном случае, прямо перед вашими обращениями к функциям Рейман, вы должны сказать:

delta = (end - start)/partitions; 

поэтому он использует новые значения конца, запуска и перегородки

Как уже говорили другие, на. 0:

Смежные вопросы