2019.05.24

ニュートン法で平方根 その3

はじめに

ニュートン法は、関数f(x)が与えられたときf(x)=0となるxを数値計算の反復によって求めるアルゴリズムの1つです。その計算式は以下です。

ニュートン法 漸化式

ここでは、ニュートン法を使って平方根を計算するメソッドの作り方を紹介します。

ニュートン法は、反復計算でf(x)=0のxの解を見つけていく方法ですが、解が見つからない場合に計算が収束せずに処理が終了できないことがあります。

メソッドの中でニュートン法を使い計算値を得ようとする場合は、解が得られない場合でも、処理を終了させて何かしらの値を戻す必要があります。このあたりのことをニュートン法平方根を計算するメソッドソースコードで詳しく説明します。

関数をf(x)=x2-aとし、f(x)=0となるxを求めることで、aの平方根を計算します。

この式は、以下の手順で導いています。

ニュートン法 平方根を求める元の式

Javaソースコード

以下がそのJavaソースコードです。

NewtonsMethod.java

001
002
003
004
005
006
007
008
009
010
011
012
013
014
015
016
017
018
019
020
021
022
023
024
025
026
027
028
029
030
031
032
033
034
035
036
037
038
039
040
041
042
043
044
045
046
047
048
049
050
051
052
053
054
055
056
057
058
059
060
061
062
063
064
065
066
public class NewtonsMethod {
	// f(x)=x^2-a
	static double f( double x, double a )
	{
		return x * x - a;
	}


	// f(x)の微分f'(x) - 接線の傾き
	static double df( double x )
	{
		return 2 * x;
	}


	// ニュートン法 漸化式
	static double newtons( double x, double a )
	{
		return x - f( x, a ) / df( x );
	}


	// ニュートン法で平方根を計算するメソッド
	static double sqrt( double a )
	{
		// 変数の宣言
		double e = 0.000001;	// 収束の判定値
		double x;		// 計算値を格納
		double x_ans;		// 1つ前の計算値

		// aが0.0以下の場合、そのままのaの値を戻す
		if ( 0.0 >= a ) return a;

		// 初期値を代入
		x_ans = 10000.0;

		// 5000回のループ
		for ( int i = 1; i <= 5000; ++ i ) {
			// ニュートン法で計算
			x = newtons( x_ans, a );

			// 収束の判定
			if ( e > Math.abs( x - x_ans ) )
				return Math.abs( x );

			// 最新の計算結果を次の計算結果に代入
			x_ans = x;
		}

		// 収束しなかった場合、マイナスの値を戻す
		return -1.0;
	}


	// メイン
	public static void main(String[] args) {
		// 変数の宣言
		double a;

		// 平方根を求める値を代入
		a = 77.7 * 77.7;

		// 結果の表示
		System.out.println( a + "の平方根: " + sqrt( a ) );
	}
}

コンパイル ソースコードが「ANSI」の場合

C:\talavax\javasample>javac -encoding sjis NewtonsMethod.java

コンパイル ソースコードが「UTF-8」の場合

C:\talavax\javasample>javac NewtonsMethod.java

実行

C:\talavax\javasample>java NewtonsMethod

6037.29(77.7×77.7)の平方根ニュートン法で計算してます。

実行結果

6037.290000000001の平方根: 77.7

平方根の計算結果が77.7になっています。

Javaソースコードの解説

ここからは、Javaソースコードを順番に説明していきます。

001
public class NewtonsMethod {

クラス名を、NewtonsMethodとしています。

002
003
004
005
006
	// f(x)=x^2-a
	static double f( double x, double a )
	{
		return x * x - a;
	}

ニュートン法でf(x)=0を求めたい関数です。ここでは、f(x)=x2-aという関数を記述しています。平方根の元の値をaに代入します。

009
010
011
012
013
	// f(x)の微分f'(x) - 接線の傾き
	static double df( double x )
	{
		return 2 * x;
	}

f(x)の微分式f'(x)を計算するメソッドです。

016
017
018
019
020
	// ニュートン法 漸化式
	static double newtons( double x, double a )
	{
		return x - f( x, a ) / df( x );
	}

ニュートン法の漸化式のメソッドです。

023
024
025
	// ニュートン法で平方根を計算するメソッド
	static double sqrt( double a )
	{

ニュートン法平方根を計算するメソッドです。double sqrt( double a)のdouble型引数aに平方根を求める値を渡せば、結果がdouble型で戻ってきます。

026
027
028
029
		// 変数の宣言
		double e = 0.000001;	// 収束の判定値
		double x;		// 計算値を格納
		double x_ans;		// 1つ前の計算値

このプログラムで使う変数を宣言しています。double型変数eは、漸化式を終了させるための値で、計算したxn+1とxn絶対値の差がe未満になったときに計算を終了させます。

031
032
		// aが0.0以下の場合、そのままのaの値を戻す
		if ( 0.0 >= a ) return a;

引数で渡された値aが0.0以下の場合、aの値をそのままメソッド戻り値にしています。a=0.0の平方根は0.0なので計算の必要がありません。また、aが0.0未満の場合には、平方根の計算ができないためaの値をそのまま戻しています。これにより、このメソッドでは戻り値が0.0未満のときに計算エラーと判断できるようにしています。

034
035
		// 初期値を代入
		x_ans = 10000.0;

計算の初期値に10000.0を代入しています。この値は任意です。、

037
038
		// 5000回のループ
		for ( int i = 1; i <= 5000; ++ i ) {

for文で5000回のループを作っています。これは5000回の計算を行った結果、計算値が収束しなかったら処理を強制終了させるものです。ループを5000回にしていることについては深い意味はありません。計算する関数f(x)によって変える必要があります。

これにより、計算結果が得られない場合でもメソッドから何かの値を返すようにしています。このメソッドの場合、for文を抜けると-1.0を返すようにしています。

039
040
			// ニュートン法で計算
			x = newtons( x_ans, a );

ニュートン法の漸化式にx_ansとaを渡して、次のxの値を取得しています。

042
043
044
			// 収束の判定
			if ( e > Math.abs( x - x_ans ) )
				return Math.abs( x );

計算した値xと、計算に使った値x_ansの差の絶対値を計算し、その値がeより小さければ計算が収束したと判断し、return文でxの絶対値を戻します。これで計算終了です。

戻す値xに絶対値をとっているのは、ニュートン法の結果がプラス/マイナスのどちらの値になるかが不明のため絶対値をとっています。どちらの値をとるかは、関数f(x)と計算の初期値によって決まります。

046
047
			// 最新の計算結果を次の計算結果に代入
			x_ans = x;

x_ansにxを代入しています。この後、計算は続きます。

050
051
		// 収束しなかった場合、マイナスの値を戻す
		return -1.0;

計算が収束せずに、for文を抜けた場合に、この処理に到達します。return文で-1.0を返してメソッド終了です。

055
056
	// メイン
	public static void main(String[] args) {

このmainメソッドからプログラムを実行します。

060
061
		// 平方根を求める値を代入
		a = 77.7 * 77.7;

平方根を求める値をdouble型変数aに代入しています。a=77.7*77.7と記述しているので、変数aに=6037.29が代入されます。

063
064
		// 結果の表示
		System.out.println( a + "の平方根: " + sqrt( a ) );

平方根を求めるメソッドで計算したaの平方根の値をコンソールに出力しています。

以上です。

関連コンテンツ

反復によって数値計算を行うアルゴリズム、ニュートン法を解説しています。興味がある方は、記事をご覧ください。

2019.05.22

関数f(x)が与えられたときf(x)=0となるxを数値計算の反復によって求める方法を詳しく解説しています。

2019.05.22

数値微分を使ったニュートン法で平方根を計算する方法を紹介しています。興味のあるかたは是非ご覧ください。

2019.05.23

処理を繰り返すために使用するfor文について解説しています。

2020.03.23

基本的な計算である足し算(加法)/引き算(減法)/掛け算(乗法)/割り算(除法)を行うプログラム作成。

2020.03.23

メソッドを抜けるときに使用するreturn文について説明しています。

2020.03.20

条件式を判断して処理を分岐する方法を詳しく説明しています。

2023.03.20

Javaのmainメソッドで受け取るパラメータについて解説しています。

2017.09.26

mainメソッドで受け取るパラメータの数の取得の仕方について解説しています。

2019.05.14

変数やクラスに格納されている値をコンソール出力する方法は?

2020.03.23

プログラムの最初に実行されるメソッドは?

2022.12.13

プログラミングで使う変数って何?

2020.03.23

Javaのプログラムを書いてみませんか?プログラムの書き方をくわしく説明しています。

2020.03.23

「Javaソースコード」から実行可能な「オブジェクトコード」に変換する方法をくわしく説明しています。

2020.03.23

Javaのプログラムを作ってみませんか?プログラミングに必要なものの用意から実行までを説明しています。

2020.03.23

Javaの学習に役立つソースコードを多数紹介しています。是非、ご覧ください。

2022.09.10

Swingパッケージを使ってグラフィック表示を行う方法を解説しています。

2020.03.23

画像フォーマット形式・色・大きさ・傾きなどの変更、特定の図形(文字・記号など)を見つけたり、取り出したりする画像処理について詳しく解説。

2015.11.29

繰り返し処理を使ったJavaのソースコードサンプルを紹介しています。

2020.03.23

配列を使うJavaソースコードを多数紹介しています。

2021.05.18

数学に関係するJavaのメソッドやソースコードなどを紹介しています。

2022.10.25

三角形、台形、円などいろいろな図形の面積を計算するプログラムを紹介しています。詳しくは、記事をご覧ください。

2021.05.18

StringクラスとStringBuilderクラスを利用したプログラミングの仕方を紹介しています。

2016.12.16

Javaを使った簡単な応用プログラム(生年月日から年齢を計算プログラムなど)を紹介しています。

2022.07.07

プログラミング、ITに関する用語をまとめています。

2022.10.17

日本で使われてきた伝統文様「和柄」について解説しています。

2022.07.27

アルゴリズムって何?

2022.12.29

平方根の意味と、Math.sqrtメソッドの使い方をソースコードを使って詳しく解説しています。

2020.03.23

メソッドの定義方法を詳しく解説しています。Javaのサンプルソースコードを使った説明もあります。

2020.03.23

プログラミング言語とは?種類や特徴について説明しています。

2022.08.03

Javaプログラムの構成について解説しています。詳しくは、こちらをご覧ください。

2020.03.23

絶対値の意味と、Math.absメソッドの使い方をソースコードを使って詳しく解説しています。

2020.03.23

繰り返し処理の作り方を解説しています。

2016.03.02

コンピュータを制御するために使用する入力機能と出力機能を持つ装置のことをコンソールといいます。興味のある方は、ご覧ください。

2020.08.24

「ゆるゆるプログラム」のコンテンツを紹介しています。興味のある方はこの記事をご覧ください。

2020.03.23

広告