Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
 
Рейтинг 4.51/41: Рейтинг темы: голосов - 41, средняя оценка - 4.51
12 / 13 / 6
Регистрация: 13.11.2012
Сообщений: 295
1

Генерирование уникальных случайных чисел заданной суммы

07.04.2019, 18:27. Показов 8209. Ответов 20
Метки нет (Все метки)

Author24 — интернет-сервис помощи студентам
Здорова ребят, есть такой код, которые генерирует уникальные числа, необходимо что сгенерированные числа, т.е их сумма была равна переменной numbers, закицлился на этот моменте.
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
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
#include "pch.h"
#include <iostream>
#include <Windows.h>
#include <ctime>
using namespace std;
 
int main()
{     
    SetConsoleOutputCP(1251);
    SetConsoleCP(1251);
    srand(time(NULL));
    int *numbers = new int;
    cout << "Введите число от 15 до 240: ";
    cin >> *numbers;
    if (*numbers > 14 && *numbers < 240) { 
        const int size = 5;
        int *arr = new int[size]; 
        bool chek_arr;
        int sum = 0;
        for (int i = 0; i <size;) { 
            chek_arr = false;
            int num_rand =  1 + rand() % 50; 
            for (int j = 0; j < i; j++) {
                if (arr[j] == num_rand) { 
                    chek_arr = true;
                    break;
 
                      }
            }   
            if (!chek_arr) {  
                sum += num_rand;  
                if ( sum == *numbers )
                arr[i] = num_rand;
                i++;
                }
            
                        
                        
        }
        for (int i = 0; i < size; i++) {
            cout << " " << arr[i] << endl;
        } 
 
        delete numbers;
        delete[] arr;
        
    } 
    else {
        cout << "Вы вышли за диапазон\n";
    }
}
0
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
07.04.2019, 18:27
Ответы с готовыми решениями:

Генерирование случайных чисел в заданном диапазоне с последующим нахождением их суммы
Генерирование набора случайных чисел. Получите заданное количество N (Например 20) случайных целых...

Генерирование случайных чисел и выборка значения из этих чисел
Здравствуйте, помогите решить задачку. Нужно случайным образом сгенерировать числа от 0..9, 100...

Rand(), генерирование случайных чисел в заданном интервале
дана функция int MyDblRand(double a,double b) надо написать так что когда будем вызывать функцию в...

Генерация уникальных случайных чисел
Приветствую. Допустим есть диапазон от 0 до 9. Как сгенерировать число так, чтобы за 10 генераций,...

20
Модератор
Эксперт С++
13507 / 10757 / 6412
Регистрация: 18.12.2011
Сообщений: 28,715
07.04.2019, 18:38 2
Это что-то слишком мудрено.
Генерите просто size-1 чисел,
а в arr[size-1] запишите разность между number и суммой всех остальных.

Не по теме:

зачем под number память выделяете динамически?

1
9 / 8 / 3
Регистрация: 09.05.2018
Сообщений: 23
07.04.2019, 18:39 3
Я возможно что-то не понял... Но вроде бы так вот работает:
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
28
29
30
31
32
33
34
#include <iostream>
#include <random>
 
 
using namespace std;
 
 
 
 
 
// main
int main( int argc, char *argv[] )
{
    srand(time(0));
 
    int number;
    cin >> number;
 
    int const first = rand()%number;
    int const second = number - first;
 
    cout << first << ", " << second << endl;
    cout << first+second << endl;
 
 
 
    return 0;
}
 
 
 
 
 
// end
0
Just Do It!
3841 / 2286 / 636
Регистрация: 23.09.2014
Сообщений: 7,073
Записей в блоге: 3
07.04.2019, 18:53 4
Цитата Сообщение от Clever411 Посмотреть сообщение
Я возможно что-то не понял.
вы правильно поняли zss )

Но если, по коду автора проинженерить задачу, то вот:
Генерируются массив из 5 случайных уникальных чисел от 1 до 50.
Этот массив будет считаться true-настоящим, если сумма элементов этого массива будет равна переменной *numbers.
1
12 / 13 / 6
Регистрация: 13.11.2012
Сообщений: 295
07.04.2019, 20:05  [ТС] 5
попробуем щас

Добавлено через 11 минут
можете код дать? у меня что-то не получается ) не совсем понял
0
9 / 8 / 3
Регистрация: 09.05.2018
Сообщений: 23
07.04.2019, 21:05 6
XLAT, Окей, понял, нужно несколько чисел, сумма которых...
names1995, Сейчас попробую написать код

Добавлено через 5 минут
Окей... Можно вот так. Только распределение будет не очень равномерным.

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
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
#include <iostream>
#include <random>
 
 
using namespace std;
 
 
 
 
 
// main
int main( int argc, char *argv[] )
{
    static constexpr int const N = 5;
 
 
 
    // prepare
    int number;
    cin >> number;
    int arr[N] = { 0 };
 
 
 
    // calc
    for(int i = 0; i < N-1; ++i)
    {
        arr[i] = rand()%number;
        number -= arr[i];
    }
    arr[N-1] = number;
 
 
 
    // output
    int summ = 0;
    for(int i = 0; i < N; ++i)
    {
        cout << arr[i] << " ";
        summ += arr[i];
    }
    cout << endl;
    cout << "summ: " << summ << endl;
 
 
 
 
    return 0;
}
 
 
 
 
 
// end
1
12 / 13 / 6
Регистрация: 13.11.2012
Сообщений: 295
07.04.2019, 21:08  [ТС] 7
да, получается неравномерное распределение, теряется уникальность
0
9 / 8 / 3
Регистрация: 09.05.2018
Сообщений: 23
07.04.2019, 21:13 8
А вот здесь всё равномерно, только сложность O(number):

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
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
#include <iostream>
#include <random>
 
 
using namespace std;
 
 
 
 
 
// main
int main( int argc, char *argv[] )
{
    static constexpr int const N = 5;
 
 
 
    // prepare
    int number;
    cin >> number;
    int arr[N] = { 0 };
 
 
 
    // calc
    for(int i = 0; i < number; ++i)
        ++arr[rand()%N];
 
 
 
    // output
    int summ = 0;
    for(int i = 0; i < N; ++i)
    {
        cout << arr[i] << " ";
        summ += arr[i];
    }
    cout << endl;
    cout << "summ: " << summ << endl;
 
 
 
 
    return 0;
}
 
 
 
 
 
// end
0
12 / 13 / 6
Регистрация: 13.11.2012
Сообщений: 295
07.04.2019, 21:18  [ТС] 9
спасибо, но в данном решение опять таки не наблюдается уникальность, все пять чисел должны быть уникальны, и вопрос как понять эту строчку, думаю достаточно туда добавить проверку на уникальность в эту часть кода
C++
1
2
   for(int i = 0; i < number; ++i)
        ++arr[rand()%N];
0
9 / 8 / 3
Регистрация: 09.05.2018
Сообщений: 23
07.04.2019, 21:21 10
Ах... Уникальность!!! А я и забыл! А "rand()%N" надо понимать как случайное число принадлежащее интервалу [0; N), ++i - я думаю объяснять не надо
1
12 / 13 / 6
Регистрация: 13.11.2012
Сообщений: 295
07.04.2019, 21:25  [ТС] 11
да, строчку догнал, но уникальность
0
9 / 8 / 3
Регистрация: 09.05.2018
Сообщений: 23
07.04.2019, 21:28 12
Этот вариант лучше, т.к. сложность его - O(N). А уникальность... надо подумать

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
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
#include <iostream>
#include <random>
 
 
using namespace std;
 
 
 
 
 
// main
int main( int argc, char *argv[] )
{
    static constexpr int const N = 5;
 
 
 
    // prepare
    int number;
    cin >> number;
    int arr[N] = { 0 };
    float arrf[N] = { 0.0f };
 
 
 
    // calc
    float summf = 0.0f;
    for(int i = 0; i < N; ++i)
    {
        arrf[i] = float(rand())/RAND_MAX;
        summf += arrf[i];
    }
 
    int summ = 0;
    for(int i = 0; i < N-1; ++i)
    {
        arr[i] = arrf[i] / summf * number;
        summ += arr[i];
    }
    arr[N-1] = number - summ;
    summ += arr[N-1];
 
 
 
    // уникальность
    // ...
 
 
 
    // output
    for(int i = 0; i < N; ++i)
    {
        cout << arr[i] << ' ';
    }
    cout << endl;
    cout << "summ: " << summ << endl;
 
 
 
 
    return 0;
}
 
 
 
 
 
// end
1
12 / 13 / 6
Регистрация: 13.11.2012
Сообщений: 295
07.04.2019, 21:41  [ТС] 13
в моем коде уникальность была, но сумма не была равна заданной сумме
0
Just Do It!
3841 / 2286 / 636
Регистрация: 23.09.2014
Сообщений: 7,073
Записей в блоге: 3
10.04.2019, 10:41 14
Лучший ответ Сообщение было отмечено names1995 как решение

Решение

names1995,
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
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
///ooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooo
/// Генерирование уникальных случайных чисел заданной суммы                    |
///ooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooo
#include <iostream>
#include <conio.h>
#include <time.h>
 
#define FOR(v)     for(size_t i = 0; i < v; ++i)
#define SHOW(v)    std::cout << #v << " = "<< v << "\n"
#define SH(v)      std::cout << v
 
///----------------------------------------------------------------------------|
///  Шаблон динамического массива.
///----------------------------------------------------------------------------:
template<class T>
class cDynamicArray 
{
public:
    cDynamicArray() : p(NULL), size(0){}
    cDynamicArray(size_t s): size(s)
    {   p = new T[size];
    }
   ~cDynamicArray()
    {   if (p) delete[] p;
    }
 
    //-------------------------------------------------------------------------|
    size_t size; // Размер массива.
    T*     p;    // Адрес массива с первым элементом.
 
    //-------------------------------------------------------------------------|
    cDynamicArray& operator=(cDynamicArray & _m)
    {   for (size_t i = 0; i < size; ++i)
        {   p[i] = _m.p[i];
        }
        return *this;
    }
    T& operator[](size_t v)  
    {   return p[v];
    }
    // Изменяем размер массива.
    void cDynamicArray<T>::resize(size_t _i)
    {   if (p) delete[] p;
        size = _i;
        p = new T[size];
    }
};
 
///----------------------------------------------------------------------------|
/// cRand_uniq
/// Генератор уникальных целых чисел из заданного диапазона.
///----------------------------------------------------------------------------:
class cRand_uniq
{
public:
    struct sDiapazon
    {   int min, maxx;
    };
 
    cRand_uniq(sDiapazon _dp) : nmax (_dp.maxx),
                                field(_dp.maxx+1 - _dp.min)
    {   dp = _dp;//number.resize(dp.maxx+1 - dp.min);
        FOR(field.size)
        {   field[i] = i + dp.min;
        }
    }
 
    void gen(cDynamicArray<int>& a )
    {   FOR(a.size)
        {   a[i] = work();
        }
    }
 
    void test()
    {   cDynamicArray<int> m(10);
        gen(m);
 
        FOR(10)
        {   SHOW(m[i]);
        }
        std::cout << "\n";
    }
 
private:
    //---------------------------------------------------------------------data:
    sDiapazon          dp;
    cDynamicArray<int> field;
    int                nmax;
    
    int work()
    {   if(nmax == dp.min)
        {   std::cout << "Error: Диапазон исчерпан!\n";
            return -1;
        }
 
        int n           = rrand(dp.maxx, dp.min);
        int res         = field[n-dp.min];       //SHOW(res);
        field[n-dp.min] = field[nmax-- -dp.min]; //SHOW(number[n-MIN]);
 
        return res;
    }
 
    int rrand(int range_max, int range_min)
    {   return rand() % (range_max - range_min + 1) + range_min;
    }
    static bool one;
 
};
 
//-----------------------------------------------------------------------------|
// Тестируем класс cRand_uniq.
//-----------------------------------------------------------------------------:
void test_cRand_uniq()
{   cRand_uniq::sDiapazon dp = {3, 10};
    cRand_uniq Task(dp);
    Task.test();
    getchar  ();
}
 
///----------------------------------------------------------------------------|
/// Структура для входных параметров.
///----------------------------------------------------------------------------:
struct sUserdata
{   int                   summa;   ///     Сумма, как входной параметр.
    size_t                amrand;  ///<<<--Кол-во уник.чисел для суммы.
    cRand_uniq::sDiapazon diapazon;///     Диапазон уникальных значений рандома.
}user_default = { 240, 7, 31, 60 };
 
///----------------------------------------------------------------------------|
/// Генерация случайных чисел с заданной суммой.
///----------------------------------------------------------------------------:
class cmyTask
{
public:
    cDynamicArray<int> numbrand; /// Здесь будут самм эти числа.
    sUserdata* user;             /// Указатель на входные данные.
    
    cmyTask(sUserdata* _user) : user(_user),
                                numbrand(_user->amrand)
    {   if(count == 0)
            srand(static_cast<unsigned int>(time(NULL)));
 
        count++;
        
        ///--------------------------------------------------------------------|
        /// Инициализируем генератор случайных чисел для
        /// диапазона от user->diapazon.min до user->diapazon.maxx :
        ///--------------------------------------------------------------------:
        cRand_uniq Rand_uniq(user->diapazon);
 
        ///--------------------------------------------------------------------|
        /// Заполняем массив numbrand[] уникальными случайными числами:
        ///--------------------------------------------------------------------:
        Rand_uniq.gen(numbrand);
 
        ///--------------------------------------------------------------------|
        /// Остальная наша задача в этой работе:
        ///--------------------------------------------------------------------:
        work();
    }
 
private:
    /// Проверяем сумму сгенерированных чисел с заданным числом summa:
    void work()
    {   int s = 0;
        FOR(user->amrand)
            s += numbrand[i];
        if(user->summa == s) show_numbrand();
    }
 
    /// Вывод на экран массива numbrand[]:
    void show_numbrand()
    {   SH("Успешная попытка: "); 
        SHOW(count);
 
        FOR(user->amrand)
            std::cout << "arr[" << i << "] = " << numbrand[i] << "\n";
        std::cout << "\n";
    }
 
    static int count; // Счетчик итераций.
};
int cmyTask::count = 0;
 
///----------------------------------------------------------------------------|
/// Тест.
///----------------------------------------------------------------------------|
int main()
{   setlocale(0, "");
 
    //test_cRand_uniq();
 
    ///------------------------------------------------------------------------|
    /// Входные данные.
    ///------------------------------------------------------------------------:
    sUserdata user = 
    {   240,    ///     Сумма, как входной параметр.
        5  ,    ///<<<--Кол-во уник.чисел для суммы.
        30 ,    ///     Минимальное  значение рандома.
        70      ///     Максимальное значение рандома.
    };
 
    while(true)
    { //cmyTask Task(&user_default);
        cmyTask Task(&user);
    }
 
    return 0;
 
}
задача решается без лайфхака от zss:
Цитата Сообщение от zss Посмотреть сообщение
а в arr[size-1] запишите разность между number и суммой всех остальных.
1
12 / 13 / 6
Регистрация: 13.11.2012
Сообщений: 295
18.04.2019, 18:28  [ТС] 15
Ругается на это
Ошибка C4596 resize: недопустимое полное имя в объявлении члена Susya v2 c:\users\drm\source\repos\susya v2\susya v2\susya v2.cpp 49
1
Just Do It!
3841 / 2286 / 636
Регистрация: 23.09.2014
Сообщений: 7,073
Записей в блоге: 3
18.04.2019, 21:28 16
Лучший ответ Сообщение было отмечено names1995 как решение

Решение

Цитата Сообщение от names1995 Посмотреть сообщение
Ругается на это
вот это:
C++
41
42
    // Изменяем размер массива.
    void cDynamicArray<T>::resize(size_t _i)
очевидно, что нужно так:
C++
41
42
    // Изменяем размер массива.
    void resize(size_t _i)
vs2010 на это по барабану, компилит на ура.

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

Добавлено через 3 минут
пофиксил, как показал выше и проверил теперь на TDM-GCC4.9.2, все работает.
1
12 / 13 / 6
Регистрация: 13.11.2012
Сообщений: 295
18.04.2019, 21:32  [ТС] 17
XLAT, все заработало, просто пока не совсем сильно разобрался в ооп, теперь у меня стоит другой вопрос, вот у нас щас генерируется числа несколько раз, и эти массивы, т.е новая генерация может совпадать с первой, надо сделать так что бы, новый массив который генерериутеся не совподал, т.е они тоже должны быть уникальны, и сгенерировать надо максимально возможную комбинацию чисел.
надеюсь внятно объяснил
0
Just Do It!
3841 / 2286 / 636
Регистрация: 23.09.2014
Сообщений: 7,073
Записей в блоге: 3
18.04.2019, 22:25 18
Цитата Сообщение от names1995 Посмотреть сообщение
сгенерировать надо максимально возможную комбинацию чисел.
максимально возможное количество уникальных массивов уникальных случайных чисел согласно заданному критерию?
количество уникальных массивов можно вычислить аналитически.
Возможно имеющийся ресурс железа(конкретно это память) не позволит получить сразу весь такой список.

Цитата Сообщение от names1995 Посмотреть сообщение
просто пока не совсем сильно разобрался в ооп
ooп это просто!
данные и методы которые работают с этим данными инкапсулируются в одной структуре(классе)
+ важная часть такой структуры это начальная инициализации подходящим из имеющихся конструктором при создании объекта этой структуры.
0
12 / 13 / 6
Регистрация: 13.11.2012
Сообщений: 295
18.04.2019, 22:33  [ТС] 19
XLAT, l
Цитата Сообщение от XLAT Посмотреть сообщение
максимально возможное количество уникальных массивов уникальных случайных чисел согласно заданному критерию?
да, именно.
Также у тебя в коде бесконечное количество выходит этих массивов. переделываю цикл на 10 итераций, допустим, но почему это не заработало)
0
Just Do It!
3841 / 2286 / 636
Регистрация: 23.09.2014
Сообщений: 7,073
Записей в блоге: 3
18.04.2019, 22:58 20
Лучший ответ Сообщение было отмечено names1995 как решение

Решение

Цитата Сообщение от names1995 Посмотреть сообщение
переделываю цикл на 10 итераций, допустим, но почему это не заработало)
потому что все 10 ваших итераций были провалены, т.е. не удовлетворили Критерий Суммы!
посмотрите номера итераций которые удовлетворяют критерию.
на первой секунде то что можно поймать в консоле 94733 номер итерации самый верхний.

но щас сделаю для 10 успешных.
вот:
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
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
///ooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooo
/// Генерирование уникальных случайных чисел заданной суммы                    |
///ooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooo
#include <iostream>
#include <conio.h>
#include <time.h>
 
#define FOR(v)     for(size_t i = 0; i < v; ++i)
#define SHOW(v)    std::cout << #v << " = "<< v << "\n"
#define SH(v)      std::cout << v
 
///----------------------------------------------------------------------------|
///  Шаблон динамического массива.
///----------------------------------------------------------------------------:
template<class T>
class cDynamicArray 
{
public:
    cDynamicArray() : p(NULL), size(0){}
    cDynamicArray(size_t s): size(s)
    {   p = new T[size];
    }
   ~cDynamicArray()
    {   if (p) delete[] p;
    }
 
    //-------------------------------------------------------------------------|
    size_t size; // Размер массива.
    T*     p;    // Адрес массива с первым элементом.
 
    //-------------------------------------------------------------------------|
    cDynamicArray& operator=(cDynamicArray & _m)
    {   for (size_t i = 0; i < size; ++i)
        {   p[i] = _m.p[i];
        }
        return *this;
    }
    T& operator[](size_t v)  
    {   return p[v];
    }
    // Изменяем размер массива.
    void resize(size_t _i)
    {   if (p) delete[] p;
        size = _i;
        p = new T[size];
    }
};
 
///----------------------------------------------------------------------------|
/// cRand_uniq
/// Генератор уникальных целых чисел из заданного диапазона.
///----------------------------------------------------------------------------:
class cRand_uniq
{
public:
    struct sDiapazon
    {   int min, maxx;
    };
 
    cRand_uniq(sDiapazon _dp) : nmax (_dp.maxx),
                                field(_dp.maxx+1 - _dp.min)
    {   dp = _dp;//number.resize(dp.maxx+1 - dp.min);
        FOR(field.size)
        {   field[i] = i + dp.min;
        }
    }
 
    void gen(cDynamicArray<int>& a )
    {   FOR(a.size)
        {   a[i] = work();
        }
    }
 
    void test()
    {   cDynamicArray<int> m(10);
        gen(m);
 
        FOR(10)
        {   SHOW(m[i]);
        }
        std::cout << "\n";
    }
 
private:
    //---------------------------------------------------------------------data:
    sDiapazon          dp;
    cDynamicArray<int> field;
    int                nmax;
    
    int work()
    {   if(nmax == dp.min)
        {   std::cout << "Error: Диапазон исчерпан!\n";
            return -1;
        }
 
        int n           = rrand(dp.maxx, dp.min);
        int res         = field[n-dp.min];       //SHOW(res);
        field[n-dp.min] = field[nmax-- -dp.min]; //SHOW(number[n-MIN]);
 
        return res;
    }
 
    int rrand(int range_max, int range_min)
    {   return rand() % (range_max - range_min + 1) + range_min;
    }
    static bool one;
 
};
 
//-----------------------------------------------------------------------------|
// Тестируем класс cRand_uniq.
//-----------------------------------------------------------------------------:
void test_cRand_uniq()
{   cRand_uniq::sDiapazon dp = {3, 10};
    cRand_uniq Task(dp);
    Task.test();
    getchar  ();
}
 
///----------------------------------------------------------------------------|
/// Структура для входных параметров.
///----------------------------------------------------------------------------:
struct sUserdata
{   int                   summa;   ///     Сумма, как входной параметр.
    size_t                amrand;  ///<<<--Кол-во уник.чисел для суммы.
    cRand_uniq::sDiapazon diapazon;///     Диапазон уникальных значений рандома.
}user_default = { 240, 7, 31, 60 };
 
///----------------------------------------------------------------------------|
/// Генерация случайных чисел с заданной суммой.
///----------------------------------------------------------------------------:
class cmyTask
{
public:
    cDynamicArray<int> numbrand; /// Здесь будут самм эти числа.
    sUserdata* user;             /// Указатель на входные данные.
    
    cmyTask(sUserdata* _user) : user(_user),
                                numbrand(_user->amrand)
    {   if(count == 0)
            srand(static_cast<unsigned int>(time(NULL)));
 
        count++;
        
        ///--------------------------------------------------------------------|
        /// Инициализируем генератор случайных чисел для
        /// диапазона от user->diapazon.min до user->diapazon.maxx :
        ///--------------------------------------------------------------------:
        cRand_uniq Rand_uniq(user->diapazon);
 
        ///--------------------------------------------------------------------|
        /// Заполняем массив numbrand[] уникальными случайными числами:
        ///--------------------------------------------------------------------:
        Rand_uniq.gen(numbrand);
 
        ///--------------------------------------------------------------------|
        /// Остальная наша задача в этой работе:
        ///--------------------------------------------------------------------:
        work();
    }
 
    bool success;
    
private:
    /// Проверяем сумму сгенерированных чисел с заданным числом summa:
    void work()
    {   success = false;
        int s = 0;
        FOR(user->amrand)
            s += numbrand[i];
        if(user->summa == s)
        {   show_numbrand();
            success = true;
        }
    }
 
    /// Вывод на экран массива numbrand[]:
    void show_numbrand()
    {   SH("Успешная попытка: "); 
        SHOW(count);
        show_numbrand_string();
        FOR(user->amrand)
            std::cout << "arr[" << i << "] = " << numbrand[i] << "\n";
        std::cout << "\n";
    }
    
    void show_numbrand_string()
    {   std::cout << "В виде строки:   ";
        FOR(user->amrand)
            std::cout << char(numbrand[i]);
        std::cout << "\n";
    }
 
    static int count; // Счетчик итераций.
};
int cmyTask::count = 0;
 
///----------------------------------------------------------------------------|
/// Тест.
///----------------------------------------------------------------------------|
int main()
{   setlocale(0, "");
 
    //test_cRand_uniq();
 
    ///------------------------------------------------------------------------|
    /// Входные данные.
    ///------------------------------------------------------------------------:
    sUserdata user = 
    {   240,    ///     Сумма, как входной параметр.
        5  ,    ///<<<--Кол-во уник.чисел для суммы.
        30 ,    ///     Минимальное  значение рандома.
        70      ///     Максимальное значение рандома.
    };
 
    int i = 0;
    while(i < 10)
    { //cmyTask Task(&user_default);
        cmyTask Task(&user);
        if(Task.success) i++;
    }
 
    return 0;
}
самая первая успешная попытка - 17

Добавлено через 7 минут
попробуйте вот тут дефолтные входные данные:
C++
1
2
3
4
5
6
    int i = 0;
    while(i < 10)
    {   cmyTask Task(&user_default); /// user_default = { 240, 7, 31, 60 };
        //cmyTask Task(&user);
        if(Task.success) i++;
    }
первая успешная итерация на полумилионник.
0
18.04.2019, 22:58
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
18.04.2019, 22:58
Помогаю со студенческими работами здесь

Генерирование случайных чисел
Пишу плеер, хочу сделать режим случайного воспроизведение музыки... делаю это так: private void...

Генерирование случайных чисел
Через Next() надо вывести случайные числа от 2 до 11, но кроме 5. Я сделал массив, и как этот...

Генерирование вещественных случайных чисел
Преподавательница сказала чтобы массив рандомно заполнялся. А в задании сказано, что массив ещё из...

Генерирование случайных чисел double
Как сгенерировать рандомные значение double в диапазоне ??


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

Или воспользуйтесь поиском по форуму:
20
Ответ Создать тему
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2024, CyberForum.ru