Método que fiz para calcular raíz sem usar Math.sqrt()

Estou iniciando o aprendizado de java. E como os exercícios do meu material estavam muito simples (e sem muito sentido), resolvi fazer algo eu mesmo. É um programa que calcula raízes, e caso ela sejam irracionais, tão próximas quanto o usuários deseja.

Queria que alguém me dissesse se tem algo no código que é desnecessário, que não está sendo usado da forma correta ou se o problema poderia ser resolvido de forma muito mais simples.

Usando esse método consegui obter a raíz de 8 com 5000 casas decimais O.o (demorou um tanto bom para calcular hehe)

[code]
import java.math.BigDecimal;
import java.math.RoundingMode;

public class RaizQuadrada {

//calcula raízes inteiras e decimais (quantas casas decimais decidir o usuário)
public static BigDecimal raiz(double num, int casas) {

    casas = casas + 3; 

    BigDecimal radicando = new BigDecimal ("" + num);

    BigDecimal decimal = new BigDecimal("1.0");
    BigDecimal i = new BigDecimal("1.0E-99");

    BigDecimal dezena = new BigDecimal("10.0");
    BigDecimal unidade = new BigDecimal("1.0");

    while(i.multiply(i).compareTo(radicando) != 0) { // enquanto i * i for diferente de num

        // se num/i * num/i for menor que num
        if (radicando.divide(i, casas, RoundingMode.UP).multiply(radicando.divide(i, casas, RoundingMode.UP)).compareTo(radicando)  == -1) {
            i = i.subtract(unidade.divide(decimal, casas, RoundingMode.UP));
            decimal = decimal.multiply(dezena);
        }

        i = i.add(unidade.divide(decimal, casas, RoundingMode.UP));

        if (i.compareTo(i.add(unidade.divide(decimal, casas, RoundingMode.HALF_EVEN))) == 0) {
                break;
        }

    }

    i = i.divide(unidade, casas - 3, RoundingMode.HALF_DOWN);
    return i;
}

}[/code]

Esse segundo método não depende do BigDecimal e nem do RoundingMode, mas em compensação, raízes irracionais terão quantas casas decimais quanto o tipo primitivo double permitir.

Ainda que seja limitado, fornece raízes que suprem a necessidade na maioria dos casos.

[code]
public class RaizQuadrada {

//Calcula raízes inteiras e decimais (casas limitadas às capacidades do tipo primitivo double) 

public static double raiz(double num) {

    double decimal = 1;
    double i = 0;

    while(i*i != num) {

        if (num/i * num/i < num) {
            i -= 1/decimal;
            decimal *= 10;
        }

        i += 1/decimal;

        if ((i + 1/decimal) == i) {
            break;
        }
    }
    return i;
}

}[/code]

Tente o Método de Newton. É muito mais rápido e elegante =).

[quote=douglas444]Estou iniciando o aprendizado de java. E como os exercícios do meu material estavam muito simples (e sem muito sentido), resolvi fazer algo eu mesmo. É um programa que calcula raízes, e caso ela sejam irracionais, tão próximas quanto o usuários deseja.

Queria que alguém me dissesse se tem algo no código que é desnecessário, que não está sendo usado da forma correta ou se o problema poderia ser resolvido de forma muito mais simples.

Usando esse método consegui obter a raíz de 8 com 5000 casas decimais O.o (demorou um tanto bom para calcular hehe)

[code]
import java.math.BigDecimal;
import java.math.RoundingMode;

public class RaizQuadrada {

//calcula raízes inteiras e decimais (quantas casas decimais decidir o usuário)
public static BigDecimal raiz(double num, int casas) {

    casas = casas + 3; 

    BigDecimal radicando = new BigDecimal ("" + num);

    BigDecimal decimal = new BigDecimal("1.0");
    BigDecimal i = new BigDecimal("1.0E-99");

    BigDecimal dezena = new BigDecimal("10.0");
    BigDecimal unidade = new BigDecimal("1.0");

    while(i.multiply(i).compareTo(radicando) != 0) { // enquanto i * i for diferente de num

        // se num/i * num/i for menor que num
        if (radicando.divide(i, casas, RoundingMode.UP).multiply(radicando.divide(i, casas, RoundingMode.UP)).compareTo(radicando)  == -1) {
            i = i.subtract(unidade.divide(decimal, casas, RoundingMode.UP));
            decimal = decimal.multiply(dezena);
        }

        i = i.add(unidade.divide(decimal, casas, RoundingMode.UP));

        if (i.compareTo(i.add(unidade.divide(decimal, casas, RoundingMode.HALF_EVEN))) == 0) {
                break;
        }

    }

    i = i.divide(unidade, casas - 3, RoundingMode.HALF_DOWN);
    return i;
}

}[/code]

Esse segundo método não depende do BigDecimal e nem do RoundingMode, mas em compensação, raízes irracionais terão quantas casas decimais quanto o tipo primitivo double permitir.

Ainda que seja limitado, fornece raízes que suprem a necessidade na maioria dos casos.

[code]
public class RaizQuadrada {

//Calcula raízes inteiras e decimais (casas limitadas às capacidades do tipo primitivo double) 

public static double raiz(double num) {

    double decimal = 1;
    double i = 0;

    while(i*i != num) {

        if (num/i * num/i < num) {
            i -= 1/decimal;
            decimal *= 10;
        }

        i += 1/decimal;

        if ((i + 1/decimal) == i) {
            break;
        }
    }
    return i;
}

}[/code][/quote]

legal a do gibdecimal.

	Se vou trabalhar com primitivo double pra raizes, costumo fazer isso:
	public double raizAdeB(double a, double b)
	{
		return Math.pow(b, 1/a);
	}