Reputation: 1010
I'am writing a program with a few files, let's assume that all includes are ok. Here is shortened code. ZZ.hpp:
class ZZ
{
public:
ZZ(ZZ const & a) { mpz_init_set(data, a.data); }
ZZ(int a = 0) { mpz_init_set_si(data, a); }
.
.
.
ZZmodN.hpp:
template <unsigned ID>
class ZZmodN
{
public:
ZZmodN() = default;
ZZmodN(ZZmodN const &) = default;
template <typename T>
ZZmodN(T const & a) : value(a) { value %= modulus; }
.
.
.
private:
ZZ value;
static ZZ modulus;
};
template <unsigned ID>
ZZ ZZmodN<ID>::modulus(19);
.
.
.
Polynomial.h:
class Polynomial{
public:
std::vector<ZZmodN<0> > co;
Polynomial(){};
Polynomial(ZZmodN<0> a){
co.push_back(a);
}
.
.
and finally Field.h:
#include "Polynomial.h"
class Field{
public:
static Polynomial f;
Polynomial poly;
Field(){}
.
.
};
Polynomial Field::f = Polynomial(1);
the problem is: I'm receiving Floating point exception when I call last (*) line, because 'modulus' = 0 when value %= modulus; is called. Why is it 0 and not 19? I checked, and ZZ constructor with 19 is called. Please help.
Upvotes: 0
Views: 130
Reputation: 7400
If you make modulus
a function, like in the code below, your problem should go away. _m
must be initialized before modulus()
can return.
template <unsigned ID>
class ZZmodN
{
public:
ZZmodN() = default;
ZZmodN(ZZmodN const &) = default;
template <typename T>
ZZmodN(T const & a) : value(a) { value %= modulus(); } // changed
// ...
private:
ZZ value;
// static ZZ modulus;
static ZZ modulus()
{
static ZZ _m(19);
return _m;
}
};
//template <unsigned ID>
//ZZ ZZmodN<ID>::modulus(19);
Upvotes: 1
Reputation: 400304
The problem you're running into is the static initialization order fiasco. In your case, the linker is deciding to initialize Field::f
before it initializes ZZmodN<0>::modulus
.
Upvotes: 6