Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
 
Рейтинг 4.83/6: Рейтинг темы: голосов - 6, средняя оценка - 4.83
3 / 3 / 2
Регистрация: 19.07.2015
Сообщений: 74
1

Функция rand() дает странные результаты

10.01.2016, 19:24. Показов 1054. Ответов 7
Метки нет (Все метки)

Есть класс Owner с таким конструктором, значения его членов определяются рандомно. В main.cpp создаются и выводятся на экран последовательно 3 объекта Owner:

C++
1
2
3
4
5
6
7
8
9
10
 Owner::Owner(std::string name)
 {
m_name=name;
    m_goodness=(rand()%10+1);
    m_size=(rand()%10+1);
    m_money=rand()%1001;
    m_agility=(rand()%10+1);
    m_int=(rand()%10+1);
    std::cout<<"Hi! I am the "<<m_name<<std::endl;
    srand(time(NULL))  };
C++
1
2
3
4
5
6
7
8
int main()
    {
        Owner breeder("breeder");
        cout<<breeder;
        Owner banker("banker");
        cout<<banker;
        Owner worker("worker");
        cout<<worker;
Результаты дохода (m_money) часто оказываются очень похожими! Результаты последних двух всегда равны, в некоторых случаях, при увеличении к-ва испытаний, результаты равны у последних трех! Часто числа в небольшом диапазоне 300-500 у всех объектов!!!
Я правильно понимаю, что это из-за использования значения времени, которое мало меняется при выполнении программы? И что делать в таком случае?
0

Помощь в написании контрольных, курсовых и дипломных работ здесь.

Лучшие ответы (1)
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
10.01.2016, 19:24
Ответы с готовыми решениями:

Rand выдает не те результаты
Здравствуйте учусь программировать, по тыкайте меня носом пожалуйста где неправильно ставлю, один...

Странные результаты деления
//Обнаружил странное исполнение функции деления в CodeBlocks 13.12 #include &lt;iostream&gt;...

Странные результаты при вычислении корней
Здравствуйте! Я тут пытаюсь написать функцию, вычисляющую корень n-ной степени(целой) числа, но...

Странные результаты вычисления синусов и косинусов
На днях выполнял задание на преоброзование полярных координат в декартовские и наоборот. Столкнулся...

7
319 / 269 / 128
Регистрация: 24.05.2012
Сообщений: 629
10.01.2016, 19:35 2
Лучший ответ Сообщение было отмечено parsecer как решение

Решение

Правильно. Что делать - вызывать srand только один раз, в самом начале main.
0
Эксперт CЭксперт С++
5064 / 2251 / 331
Регистрация: 20.02.2013
Сообщений: 5,602
Записей в блоге: 19
10.01.2016, 20:33 3
Цитата Сообщение от Кот Ангенс Посмотреть сообщение
Правильно. Что делать - вызывать srand только один раз, в самом начале main.
Вызывать srand() можно и в пользовательской функции. Но вызывать её надо перед вызовом функции rand(), и только один раз. Сделать это можно, указав перед srand() ключевое слово static.

C++
1
2
3
4
5
6
7
8
9
10
11
Owner::Owner(std::string name)
{
    static srand(time(NULL));
    m_name=name;
    m_goodness=(rand()%10+1);
    m_size=(rand()%10+1);
    m_money=rand()%1001;
    m_agility=(rand()%10+1);
    m_int=(rand()%10+1);
    std::cout << "Hi! I am the " << m_name <<std::endl;
}
0
319 / 269 / 128
Регистрация: 24.05.2012
Сообщений: 629
10.01.2016, 22:21 4
Цитата Сообщение от gru74ik Посмотреть сообщение
Вызывать srand() можно и в пользовательской функции. Но вызывать её надо перед вызовом функции rand(), и только один раз.
Разумеется. Я лишь предложил самый простой вариант, где это можно сделать. Вообще правильнее было бы вызывать в конструкторе приватного статического объекта-одиночки.

Код с static srand(time(NULL)); не компилируется:
C89/C99/C11/GNU89/GNU99/GNU11:
Код
test.c:21:18: error: expected declaration specifiers or ‘...’ before ‘time’
C++03/C++11/C++14/C++1y:
Код
test.cpp:12:18: error: ISO C++ forbids declaration of ‘srand’ with no type [-fpermissive]
C++ считает, что я пытаюсь объявить прототип функции srand, но забыл тип возвращаемого значения.
Не уверен, что понял правильно сообщение от компилятора C, но, вроде бы, он думает, что я забыл указать тип параметра time в прототипе функции srand.
0
1367 / 590 / 199
Регистрация: 02.08.2011
Сообщений: 2,882
10.01.2016, 23:03 5
Цитата Сообщение от gru74ik Посмотреть сообщение
Вызывать srand() можно и в пользовательской функции. Но вызывать её надо перед вызовом функции rand(), и только один раз. Сделать это можно, указав перед srand() ключевое слово static.
последствие моих советов?
На каждом новом запуске программы будет одна и та же последовательность. Это до random из c++11. Такое вот есть отличие.

Цитата Сообщение от Кот Ангенс Посмотреть сообщение
static srand(time(NULL));
C++
1
static int srand(time(NULL)); //Типа -то и не было, теперь вон он, int есть
но как я написал, на каждом новом запуске программы будут генерироваться одни и те же значения.
Сразу после main srand. Совет поста 2.
0
319 / 269 / 128
Регистрация: 24.05.2012
Сообщений: 629
10.01.2016, 23:09 6
Цитата Сообщение от daslex Посмотреть сообщение
static int srand(time(NULL));
Но ведь это означает static int srand = time(NULL);, то есть мы объявляем локальную статичную переменную srand и присваиваем ей текущее время (еще и с downcast'ом от time_t {aka long} к int).
0
1367 / 590 / 199
Регистрация: 02.08.2011
Сообщений: 2,882
10.01.2016, 23:57 7
Ну да. Так и есть. Не нравится? Тогда можно использовать медленный вариант.
C++
1
2
3
#include <ctime>
#include <cstdlib>
#include <windows.h>
C++
1
2
3
4
    srand(clock());
    Sleep(1);
   //Всякие рэнды
 cout << rand()%50 << ' ';
Добавлено через 1 минуту
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
#include <iostream>
#include <ctime>
#include <cstdlib>
#include <windows.h> //Sleep
 
using namespace std;
 
int foo() {
    srand(clock());
    Sleep(1);
    cout << rand() % 50 << ' ';
    return 0;
}
 
int main() {
 
    foo();
    foo();
 
    foo();
    foo();
 
    foo();
    foo();
 
    cin.get();
}
Добавлено через 22 минуты
static srand(time(NULL));
Не выйдет, потому как здесь происходит попытка использовать static в месте вызова функции для вызова функции как для переменной, а не для обозначения переменной как переменной.
Это так же как вот эта, весьма странная конструкция (не рабочая и не должна работать)
C++
1
2
3
4
void foo(){}
int main() {
    static foo();
}
0
Эксперт CЭксперт С++
5064 / 2251 / 331
Регистрация: 20.02.2013
Сообщений: 5,602
Записей в блоге: 19
11.01.2016, 06:12 8
Цитата Сообщение от daslex Посмотреть сообщение
последствие моих советов?
Ахахаха, точняк

Ну, тогда, вот такой костыль:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
Owner::Owner(std::string name)
{
    static bool first_time_in_this_program = true;
    if (first_time_in_this_program)
    {
        srand(time(NULL));
        first_time_in_this_program = false;
    }
    m_name=name;
    m_goodness=(rand()%10+1);
    m_size=(rand()%10+1);
    m_money=rand()%1001;
    m_agility=(rand()%10+1);
    m_int=(rand()%10+1);
    std::cout << "Hi! I am the " << m_name <<std::endl;
}
Добавлено через 1 минуту
Или, как верно сказал Кот Ангенс, использовать Singleton.
0
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
11.01.2016, 06:12

Функция rand()
Помогите, как сделать так что бы функция random при каждом запросе к ней генерировала случайное...

Функция rand
Помогите написать программу) В цикле, используя функцию rand генерировать числа в диапазоне от 0...

Функция rand()
Здравствуйте, имеется код с реализацией алгоритма прямого поиска и я не могу понять как задается...

Функция rand
Решить задачу с использованием библиотечной функции rand,заголовочный файл stdlib.h Случайные...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
8
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2021, vBulletin Solutions, Inc.