2010-06-29 10 views
4

У меня есть приложение QT, в котором работает еще 2 потока.qrand не генерирует случайное число

Внутри потоков я использую функцию qrand для генерации случайного числа. Ниже приведен код, используемый для получения номера, где m_fluctuations max является двойным.

int fluctuate = qrand() % (int)(m_FluctuationMax * 100); 

Я попытался добавить следующий код в основной поток, а также внутри классов потоков.

QTime now = QTime::currentTime(); 
qsrand(now.msec()); 

Проблема в том, что генерируемые значения всегда одинаковы при каждом запуске приложения.

Разве они не будут отличаться, так как семя задается значением 'currentTime()'.

Благодаря

ответ

8

у меня был свой qsrand() в конструктор потока/класса. Когда я переместил его в функцию run(), он начал работать случайным образом. Не уверен, почему это не сработает от конструктора. Спасибо всем за вашу помощь.

+10

FYI: он не работал с конструктором, потому что 'qsrand()' [хранит семя в потоке-локальном хранилище] (http://doc.qt.nokia.com/latest/qtglobal.html#qsrand) (независимые значения для каждого потока). При помещении вызова в конструктор семя инициализируется в одном потоке и используется в другом. При помещении вызова в метод 'run()' семя инициализируется в том же потоке, который вызывает 'qrand()'. –

2

первой вещь, которую я бы проверить это значение now.msec(). Он возвращает только миллисекундную часть текущего времени и состояния doco:

Обратите внимание, что точность зависит от точности базовой операционной системы; не все системы обеспечивают точность в 1 миллисекунду.

Возможно, ваша платформа всегда возвращает то же значение для msec(). Если это так, вы можете попытаться использовать минуты и секунды как-то (при условии, что вы не используете свой код несколько раз в секунду).

Вы не указали, на какой платформе вы работаете, но исходный код Qt поддерживает только подсетовое разрешение, если установлен либо Q_OS_WIN, либо Q_OS_UNIX.


Имейте в виду, что случайные числа для каждого потока, так что вы, вероятно, следует сделать qsrand в каждый нить, чтобы она автоматически затравку 1.

+0

Я проверил, что теперь и значение мс отличается когда-либо время, но случайное число же каждый раз. –

+0

@Michael, _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ – paxdiablo

+0

Также установлено значение m_Fluctuation_Max? И, если вы всегда получаете одинаковый номер, что это? – paxdiablo

2

У меня был qsrand() в конструкторе thread/class. Когда я переместил его в функцию run(), он начал работать случайным образом. Не уверен, почему это не сработает от конструктора.

qsrand() использует внутрипотоковое хранение для хранения семян, которые на самом деле состояние генератора псевдослучайных чисел, который также обновляется при каждом вызове qrand(). Если вы выберете PRNG за пределами потока, где вы будете его использовать, это семя не влияет на результат. По-умолчанию локальное хранилище по умолчанию равно нулю, поэтому каждый раз, когда семя всегда будет одинаковым, вы будете получать одну и ту же последовательность псевдоданных.

3

Это может помочь любому, кто случилось иметь подобную проблему:

qsrand(static_cast<quint64>(QTime::currentTime().msecsSinceStartOfDay())); 

array<int, 5> arr = {qrand(), qrand(), qrand(), qrand(), qrand()}; 

for(auto i : arr) 
    cout << i << endl; 
Смежные вопросы