三次方程式の解を求めるには??


理恵  2003-10-21 00:30:25  No: 5320  IP: [192.*.*.*]

三次方程式の解を求める関数のようなものはないのでしょうか?
やはり、自分でプログラムを書かないとだめなのでしょうか?

編集    削除
にしの  2003-10-21 05:26:45  No: 5321  IP: [192.*.*.*]

3次方程式であれば、公式があったと思います。
汎用的にするのであれば、ニュートン法などのアルゴリズムを使用することになります。

編集    削除
通りすがり  2003-10-21 06:29:08  No: 5322  IP: [192.*.*.*]

カルダノ?

編集    削除
にしの  2003-10-21 09:45:42  No: 5323  IP: [192.*.*.*]

一般的にはそうですね。
タルタリアに無断で発表したとか。

公式をそのままコーディングすると、立方根が必要になりそうです。
立方根も、結局ニュートン法で近似値を出すことになるでしょうから、素直にニュートン法にしておいた方が無難かも。

編集    削除
通りすがり  2003-10-21 20:12:37  No: 5324  IP: [192.*.*.*]

>タルタリアに無断で発表したとか。
かわいそうなタルタリア。。。(TT)
本題に関係なかったっすネ!!失礼しました。

編集    削除
にしの  2003-10-23 07:40:23  No: 5325  IP: [192.*.*.*]

「C言語による最新アルゴリズム辞典」(技術評論社 ISBN4-87408-414-1)のニュートン法をそのままDelphiにしてみました。

元が(C++でなく)Cですので、参考程度に。

var
  b,c,d: double;

function f(x: double): double;
begin
//x^3+bx^2+cx+d
  Result := ((b + x) * x + c) * x + d;
end;

function f_prime(x: double): double;
begin
//3x^2+2bx+c (f()の導関数)
  Result := (2 * b + 3 * x) * x + c;
end;

function newton(x: double): double;
var
  fx, fp, xprev: double;
begin
  while true do
  begin
    fx := f(x);
    fp := f_prime(x);
    if fp = 0 then fp := 1;
    xprev := x;
    x := x - (fx / fp);

    if x = xprev then Break;
  end;
  Result := x;
end;

procedure TForm1.Button1Click(Sender: TObject);
var
  a, x1, x2, x3: double;
begin
  a := StrToFloatDef(Edit1.Text, 1);
  b := StrToFloatDef(Edit2.Text, 1);
  c := StrToFloatDef(Edit3.Text, 1);
  d := StrToFloatDef(Edit4.Text, 1);
  b := b / a;
  c := c / a;
  d := d / a;
  a := b * b - 3 * c;
  if a > 0 then
  begin
    a := (2.0 / 3.0) * sqrt(a);
    x1 := newton(-a - b / 3);
    x2 := newton( a - b / 3);
    Edit5.Text := FloatToStr(x1);
    Edit6.Text := FloatToStr(x2);
    Edit7.Text := '';
    if x1 <> x2 then
    begin
      x3 := newton(     b / (-3));
      Edit7.Text := FloatToStr(x3);
    end;
  end
  else
  begin
    Edit5.Text := '';
    Edit6.Text := '';
    Edit7.Text := '';
    x1 := newton(0);
    Edit5.Text := FloatToStr(x1);
  end;
end;

編集    削除