У меня есть класс с членом mersenne_twister_engine, который я хочу инициализировать с помощью seed_seq, созданного из строки.Сначала я попробовал это:
class A
{
private:
std::mt19937_64 rng;
public:
A(std::string seed) : rng(std::seed_seq(seed.begin(), seed.end())) { }
};
Но это не компилируется, потому что:
(...) cannot convert argument 1 from 'std::seed_seq' to '_Seed_seq &'
Я могу заставить его работать так:
class B
{
private:
std::mt19937_64 rng;
public:
B(std::string seed)
{
std::seed_seq seedSeq(seed.begin(), seed.end());
rng = std::mt19937_64(seedSeq);
}
};
Но если я правильно понимаю, переменная-член rng теперь будет построена дважды, поэтому, если возможно, я бы хотел этого избежать. Итак, мой главный вопрос: Возможно ли сделать эту работу без инициализации rng дважды?
Прежде чем кто-либо предлагает, я также пытался использовать отдельный членфункция для создания объекта seed_seq, но единственный способ, которым я могу заставить его скомпилировать, - это вернуть константную ссылку следующим образом:
class C
{
private:
std::mt19937_64 rng;
const std::seed_seq& makeSeedSeq(std::string seed)
{
return std::seed_seq(seed.begin(), seed.end());
}
public:
C(std::string seed) : rng(makeSeedSeq(seed)) { }
};
Класс C выполняет компиляцию, но при тестировании с разными строками результатывсегда то же самое и всегда, как если бы семя было пустой строкой.Я думаю, это потому, что makeSeedSeq возвращает ссылку на локальный, и результатом является неопределенное поведение? Это отступление , но если бы кто-то мог объяснить это и, возможно, почему seed_seq был реализован таким образом, я был бы очень признателен.