[SML 7884] Re: 連想計算というリフレクティブな手法

Narita Takaoki Narita.Takaoki @ exc.epson.co.jp
2010年 12月 17日 (金) 18:09:45 JST


成田です。

> 佐原です。

Smalltalk じゃない言語でズンズン行くのもなんですけれど、

> VDM++だと、高階関数使ってもリフレクション的なことはできそうもな
> いので、数値アルゴリズムで作りました :-)

こんなん書いてみました:

class Sequential_Square

functions
  static public  sequential_square :
	((nat * nat) -> (nat * nat)) * nat1
		+> ((nat * nat) -> (nat * nat))
  sequential_square (T, n) ==
    if (n = 1) then
      T
    else
      if (n rem 2 = 1) then
        (sequential_square(T, n - 1)) comp T
      else
        (sequential_square(T, floor(n / 2))) ** 2;

end Sequential_Square

class Fibonacci is subclass of Sequential_Square

functions
  static public  fibo : (nat * nat) +> (nat * nat)
  fibo (pre_f) ==
    mk_(pre_f.#1 + pre_f.#2, pre_f.#1);

  static public  fibonacci : nat1 +> nat
  fibonacci (n) ==
    if (n = 1) then
      1
    else
      ((sequential_square (fibo, n - 1))(mk_(1,0))).#1;

end Fibonacci

Sequential_Square が中途半端で気持ち悪いのですが、多相型関数の定義が
よくわからなくて型チェックではじかれたので、こんな感じになってしまいました。

高階関数を駆使して関数合成で問題を解く設計を書こうとすると、関数の型宣言
で死にそうになる気がする・・・ことに汎用性を持たせようとすると・・・

Haskell とかも死にそうになるけど、まだしも・・・

関数に対する comp と ** 演算子は便利。ぶっちゃけ、整数値が戻ってくる範
囲では sequential_square (T, n) == T ** n; で十分速い。

> リフレクション使うより速いので、シンボリック実行しているVDM++インタープリ
> タでも、fastFib(-1)からfastFib(100)まで
> 全部計算しても、一瞬で終わりますが、多倍長計算できないのでfastFib(92)=
> 7540113804746369024までしか計算できません。

環境の違いでしょうか?fibonacci(78) までしか計算できませんでした。それより
上もいけたですが、値が浮動小数点数。さらに fibonacci(10000) だと "1.#INF"
などと戻ってきているようです。とりあえず戻ってくることは、戻ってくる。

# 当方、VDM++VICE。

--
セイコーエプソン株式会社 機器ソフトウェア統括センター
 成田 隆興  Tel. 0263-58-8464 (職場代表電話)


SML メーリングリストの案内