Код работает с плавающими Boost Multiprecision Library, но не с бэкэндом GMP

Я учусь использовать Boost Multiprecision Library. В качестве упражнения, следуя следующему примеру построения распределения, я смог успешно реализовать функцию, которая вычисляет отрицательный биномиальный PDF с высокой точностью, используя встроенное в библиотеку представление высокой точности десятичного числа с плавающей запятой cpp_def_float:

#include <iostream>
#include <boost/math/distributions/negative_binomial.hpp>
#include <boost/multiprecision/cpp_dec_float.hpp>

using namespace std;
using namespace boost;
typedef boost::multiprecision::cpp_dec_float_50 myPrecision;

template <class T1, class T2>
myPrecision negbinPDF(T1 passed_val, T2 passed_par1, T2 passed_par2)
{
    myPrecision val = myPrecision(passed_val);
    myPrecision par1 =  myPrecision(passed_par1);
    myPrecision par2 = myPrecision(passed_par2);

    return math::pdf(math::negative_binomial_distribution<myPrecision>(par1, par2), val);
};


int main()
{
    auto p = negbinPDF(1.23456789012345678901234567890, 8.0, 0.25);
    cout << "The PDF is: " << p << endl;
}

Работает как положено, выводит следующий вывод:

The PDF is: 0.0001263

Однако я хочу изменить приведенный выше код для использования бэкэнда GMP. Как я понял отсюда, это было бы просто вопросом включения gmp.hpp и используя правильный тип плавающего GMP вместо cpp_def_flota, Как следующее:

#include <iostream>
#include <boost/math/distributions/negative_binomial.hpp>
#include <boost/multiprecision/gmp.hpp>

using namespace std;
using namespace boost;
typedef boost::multiprecision::number<boost::multiprecision::gmp_float<50>> myPrecision;
// typedef boost::multiprecision::mpf_float_50 myPrecision; // this also raises the errors

template <class T1, class T2>
myPrecision negbinPDF(T1 passed_val, T2 passed_par1, T2 passed_par2)
{
    myPrecision val = myPrecision(passed_val);
    myPrecision par1 =  myPrecision(passed_par1);
    myPrecision par2 = myPrecision(passed_par2);

    return math::pdf(math::negative_binomial_distribution<myPrecision>(par1, par2), val);
};


int main()
{
    auto p = negbinPDF(1.23456789012345678901234567890, 8.0, 0.25);
    cout << "The PDF is: " << p << endl;
}

Тем не менее, это не работает, вызывая следующие ошибки компиляции (сначала я показываю здесь только несколько; позже я делаю ссылку на полный журнал ошибок):

/tmp/cc6JpzDu.o: In function `boost::multiprecision::backends::detail::gmp_float_imp<50u>::~gmp_float_imp()':
to_ask_at_SO.cpp:(.text._ZN5boost14multiprecision8backends6detail13gmp_float_impILj50EED2Ev[_ZN5boost14multiprecision8backends6detail13gmp_float_impILj50EED5Ev]+0x21): undefined reference to `__gmpf_clear'
/tmp/cc6JpzDu.o: In function `boost::multiprecision::backends::gmp_float<50u>::gmp_float()':
to_ask_at_SO.cpp:(.text._ZN5boost14multiprecision8backends9gmp_floatILj50EEC2Ev[_ZN5boost14multiprecision8backends9gmp_floatILj50EEC5Ev]+0x31): undefined reference to `__gmpf_init2'
/tmp/cc6JpzDu.o: In function `boost::multiprecision::backends::detail::gmp_float_imp<50u>::str[abi:cxx11](long, std::_Ios_Fmtflags) const':
to_ask_at_SO.cpp:(.text._ZNK5boost14multiprecision8backends6detail13gmp_float_impILj50EE3strB5cxx11ElSt13_Ios_Fmtflags[_ZNK5boost14multiprecision8backends6detail13gmp_float_impILj50EE3strB5cxx11ElSt13_Ios_Fmtflags]+0xbe): undefined reference to `__gmp_get_memory_functions'
to_ask_at_SO.cpp:(.text._ZNK5boost14multiprecision8backends6detail13gmp_float_impILj50EE3strB5cxx11ElSt13_Ios_Fmtflags[_ZNK5boost14multiprecision8backends6detail13gmp_float_impILj50EE3strB5cxx11ElSt13_Ios_Fmtflags]+0x132): undefined reference to `__gmpf_get_str'
to_ask_at_SO.cpp:(.text._ZNK5boost14multiprecision8backends6detail13gmp_float_impILj50EE3strB5cxx11ElSt13_Ios_Fmtflags[_ZNK5boost14multiprecision8backends6detail13gmp_float_impILj50EE3strB5cxx11ElSt13_Ios_Fmtflags]+0x1b3): undefined reference to `__gmpf_get_str'
to_ask_at_SO.cpp:(.text._ZNK5boost14multiprecision8backends6detail13gmp_float_impILj50EE3strB5cxx11ElSt13_Ios_Fmtflags[_ZNK5boost14multiprecision8backends6detail13gmp_float_impILj50EE3strB5cxx11ElSt13_Ios_Fmtflags]+0x30f): undefined reference to `__gmpf_get_str'
to_ask_at_SO.cpp:(.text._ZNK5boost14multiprecision8backends6detail13gmp_float_impILj50EE3strB5cxx11ElSt13_Ios_Fmtflags[_ZNK5boost14multiprecision8backends6detail13gmp_float_impILj50EE3strB5cxx11ElSt13_Ios_Fmtflags]+0x343): undefined reference to `__gmpf_get_str'
/tmp/cc6JpzDu.o: In function `boost::multiprecision::backends::detail::gmp_float_imp<50u>::operator=(double)':
to_ask_at_SO.cpp:(.text._ZN5boost14multiprecision8backends6detail13gmp_float_impILj50EEaSEd[_ZN5boost14multiprecision8backends6detail13gmp_float_impILj50EEaSEd]+0x36): undefined reference to `__gmpf_init2'
to_ask_at_SO.cpp:(.text._ZN5boost14multiprecision8backends6detail13gmp_float_impILj50EEaSEd[_ZN5boost14multiprecision8backends6detail13gmp_float_impILj50EEaSEd]+0x4f): undefined reference to `__gmpf_set_d'
/tmp/cc6JpzDu.o: In function `boost::multiprecision::backends::detail::gmp_float_imp<50u>::gmp_float_imp(boost::multiprecision::backends::detail::gmp_float_imp<50u> const&)':
to_ask_at_SO.cpp:(.text._ZN5boost14multiprecision8backends6detail13gmp_float_impILj50EEC2ERKS4_[_ZN5boost14multiprecision8backends6detail13gmp_float_impILj50EEC5ERKS4_]+0x28): undefined reference to `__gmpf_init2'
to_ask_at_SO.cpp:(.text._ZN5boost14multiprecision8backends6detail13gmp_float_impILj50EEC2ERKS4_[_ZN5boost14multiprecision8backends6detail13gmp_float_impILj50EEC5ERKS4_]+0x48): undefined reference to `__gmpf_set'

Полный журнал ошибок можно увидеть здесь.

У меня вопрос только, что я делаю неправильно, как я могу заставить эту работу работать с бэкэндом GMP? Если это поможет, я использую Visual Code в 64-битной установке Ubuntu 18.04.

0 ответов

Другие вопросы по тегам