///Bilgisayar programlama II ve Sayısal Çözümleme
//ÖDEV 8
// f(x)=ln(x^2)-0.7 fonksiyonunun x0=0 x1=4 ilktahminini kulanarak 
// ridder  yöntemi ile kökünü bulmak için bir 
// program geliştiriniz, kök değerini hesaplatınız 

import java.util.*;
import java.awt.*;
import java.applet.Applet;
import java.awt.event.*;
import javax.swing.*;
//============= Tanımı gereken fonksiyon ================

class fb extends f_x
{
   public double func (double x)
   { return Math.log(x*x)-0.7;}
}

public class FSCO8
{
// Ridder Metodu ile lineer olmıyan denklemlerin köklerinin bulunması
//referans : Numerical Recipes in C, second edition, William H. Press, 
//Saul A. Teukolsky, William T. Vetterling, Brian P. Flannery
//cambridge university press

public static double SIGN(double a,double b)
{
return Math.abs(a)*b/Math.abs(b);
}

public static double ridder(f_x f, double x1, double x2)
{double xacc=1.0e-9;
 return ridder(f, x1,x2,xacc);
}

public static double ridder(f_x f, double x1, double x2, double xacc)
{  
	int NRANSI;
	int MAXIT=64;
	double UNUSED=-1.11e30;
	int j;
	double ans,fh,fl,fm,fnew,s,xh,xl,xm,xnew;

	fl=f.func(x1);
	fh=f.func(x2);
	if ((fl > 0.0 && fh < 0.0) || (fl < 0.0 && fh > 0.0)) {
		xl=x1;
		xh=x2;
		ans=UNUSED;
		for (j=0;j<MAXIT;j++) {
			xm=0.5*(xl+xh);
			fm=f.func(xm);
			s=Math.sqrt(fm*fm-fl*fh);
			if (s == 0.0) return ans;
			xnew=xm+(xm-xl)*((fl >= fh ? 1.0 : -1.0)*fm/s);
			if (Math.abs(xnew-ans) <= xacc) return ans;
			ans=xnew;
			fnew=f.func(ans);
			if (fnew == 0.0) return ans;
			if (SIGN(fm,fnew) != fm) {
				xl=xm;
				fl=fm;
				xh=ans;
				fh=fnew;
			} else if (SIGN(fl,fnew) != fl) {
				xh=ans;
				fh=fnew;
			} else if (SIGN(fh,fnew) != fh) {
				xl=ans;
				fl=fnew;
			} else System.out.println("bu noktaya asla ulaşamayız.");
			if (Math.abs(xh-xl) <= xacc) return ans;
		}
		System.out.println("ridder metodu maksimum iterasyon sayısını aştı");
	}
	else {
		if (fl == 0.0) return x1;
		if (fh == 0.0) return x2;
		System.out.println("ridderde verilen sınırlar arasında kök mevcut değil");
	}
	return 0.0;
}
     public static void main (String args[])  
     {
	 fb f=new fb();         
     double a,b;
     a=Double.parseDouble(JOptionPane.showInputDialog(" Fonksiyonun alt sınırını giriniz a : "));
     b=Double.parseDouble(JOptionPane.showInputDialog(" Fonksiyonun üst sınırını giriniz b : "));
     double r;
     r= ridder(f,a,b);
     JOptionPane.showMessageDialog(null," kök değeri  : "+r+"\nFonksiyon değeri : "+f.func(r),
     "Ridder yöntemiyle kök hesabı : ",JOptionPane.PLAIN_MESSAGE);
     System.exit(0);
     } 
}