Boostの数学関数

この記事はBoost Advent Calendar 2011の参加記事です。

Boostの数学ライブラリの一部を紹介したいと思います。

複素関数としての逆三角関数・逆双曲線関数

C99の逆三角関数・逆双曲線関数を移植したものです。C++11に追加されたので、そのうち新規には使われなくなるかもしれませんが……。

三角関数・逆双曲線関数は多価関数なのでどういった分枝を取るかが問題になります。分枝についてBoostのドキュメントに書かれていないので明記しておきます。

arccos

#include <boost/math/complex/acos.hpp>

template <typename T> 
std::complex<T> acos(const std::complex<T>& z);

上で、実関数としてのと一致し、で連続となるように分枝をとります。

arcsin

#include <boost/math/complex/asin.hpp>

template <typename T> 
std::complex<T> asin(const std::complex<T>& z);

上で、実関数としてのと一致し、で連続となるように分枝をとります。

arctan

#include <boost/math/complex/atan.hpp>

template <typename T> 
std::complex<T> atan(const std::complex<T>& z);

実軸上で実関数としてのと一致し、で連続となるように分枝をとります。

arccosh

#include <boost/math/complex/acosh.hpp>

template <typename T> 
std::complex<T> acosh(const std::complex<T>& z);

で実関数としてのと一致し、で連続となるように分枝をとります。

arcsinh

#include <boost/math/complex/asinh.hpp>

template <typename T>
std::complex<T> asinh(const std::complex<T>& z);

実軸上で実関数としてのと一致し、で連続となるように分枝をとります。

arctanh

#include <boost/math/complex/atanh.hpp>

template <typename T>
std::complex<T> atanh(const std::complex<T>& z);

で実関数としての
と一致し、で連続となるように分枝をとります。

特殊関数

Boostには特殊関数が大量にあります。数が多いので関数そのものについてはリストをあげるだけにします。

ポリシー
Boostの特殊関数ライブラリでは、ポリシークラスで挙動をカスタマイズできます。ポリシーでカスタマイズできるのは

  1. エラーハンドリングの方法
  2. 関数の内部で用いる浮動小数点数型
  3. 精度
  4. 計算の繰り返し回数の上限
  5. 数学的に意味のない操作をコンパイル時に弾くかどうか
  6. 結果が整数であるべき時の返り値の型および丸めの方法

の6つです。最後の2つは特殊関数を扱う上ではほとんど関係ありません。

ポリシーを指定する方法は

  1. マクロによりデフォルトの挙動を指定
  2. マクロにより名前空間内・翻訳単位内での挙動を変える
  3. 関数呼び出し時にポリシークラスのオブジェクトを渡す

の3通りあります。

マクロでデフォルトの挙動を指定するのは最も手軽な方法です。コンパイルオプションでマクロを定義することにより、ソースコードを書き換えずに挙動を変えられるというメリットがあります。しかし、異なる翻訳単位で異なる挙動を指定するとOne Definition Rule違反によりその動作は未定義となってしまうので注意が必要です。

One Definition Rule違反を気にせずカスタマイズしたい場合は、名前空間単位・翻訳単位において挙動を指定します。名前空間fooで指定したい場合は、

#include <boost/math/special_functions.hpp>

namespace foo {
typedef boost::math::policies::policy</* ポリシーの指定 */> my_policy;
BOOST_MATH_DECLARE_SPECIAL_FUNCTIONS(my_policy);
} // namespace foo

のように書きます。こうすると、例えばガンマ関数なら

foo::tgamma(1.0)

のように書くと、指定したポリシーに従った関数を使えます。

広い範囲で指定されたポリシーではなく、個々の関数で異なるポリシーを使いたい場合は、単に関数呼び出しの際に指定するだけです。

その他の数学ライブラリ

今回紹介した数学ライブラリの他に、Boostには

  1. 最大公約数・最小公倍数
  2. 確率分布
  3. 八元数
  4. 線形代数

等のライブラリがあります。Boostの非常に充実していますので、是非ご活用ください。