Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
 
Рейтинг 4.80/40: Рейтинг темы: голосов - 40, средняя оценка - 4.80
0 / 0 / 5
Регистрация: 20.12.2016
Сообщений: 152
1

Функция: заполнить массив случайными значениями (с использованием указателей)

24.06.2017, 21:01. Показов 7755. Ответов 23
Метки нет (Все метки)

Author24 — интернет-сервис помощи студентам
подскажите.
есть вот такая задача
Написать ф-цию fill, которая принимает указатель на массив и количество элементов. Ф-ция заполняет массив случайными значениями.
не могу понять как сделать эту задачу с использованием указателей.только начал их изучать и очень путаюсь
0
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
24.06.2017, 21:01
Ответы с готовыми решениями:

Заполнить массив случайными значениями
Написать программу, в которой с помощью генератора случайных значений сформировать 4 массива V1,...

Заполнить массив случайными значениями
Здравствуйте. Помогите, пожалуйста, с задачей. С++ Заполните массив из N элементов случайными...

заполнить массив случайными значениями
Пожалуйста помогите решать задачу. Внести в память матрицу 3х4. Заполнить ее случайными...

Заполнить массив случайными значениями
и так, мне надо сделать такую штуку: делаю массив (8 чисел), заполняю его рандомными числами, и...

23
12 / 12 / 10
Регистрация: 04.06.2017
Сообщений: 99
24.06.2017, 21:46 2
swswsss, держи, вроде работает
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
#include "stdafx.h"
#include <iostream>
#include <cstdlib>
#include <ctime>
 
using namespace std;
 
int fill(int* p) {
    while (*p) {
        *p = rand();
        p++;
    }
    return *p;
}
 
int main()
{
    srand(time(0));
    int array[5];
    int *ptr = array;
    fill(array);
    for (int i = 0; i < 5; i++)
        cout << *(ptr + i) << endl;
    system("pause");
    return 0;
}
0
nd2
3438 / 2817 / 1249
Регистрация: 29.01.2016
Сообщений: 9,426
24.06.2017, 21:59 3
Цитата Сообщение от savenkodenys Посмотреть сообщение
C++
1
while (*p)
И когда произойдёт выход из цикла?
Цитата Сообщение от savenkodenys Посмотреть сообщение
C++
1
return *p;
Зачем return?
0
12 / 12 / 10
Регистрация: 04.06.2017
Сообщений: 99
24.06.2017, 22:02 4
nd2,
Цитата Сообщение от nd2 Посмотреть сообщение
И когда произойдёт выход из цикла?
когда указатель будет равен нулю, а это конец массива
Цитата Сообщение от nd2 Посмотреть сообщение
Зачем return?
Согласен, return был лишним. Просто быстро написал код, не подумал
0
nd2
3438 / 2817 / 1249
Регистрация: 29.01.2016
Сообщений: 9,426
24.06.2017, 22:04 5
Цитата Сообщение от savenkodenys Посмотреть сообщение
когда указатель будет равен нулю, а это конец массива
Тут не указатель проверяется, а содержимое по указателю. И почему в конце массива указатель (адрес) будет равен нулю?
0
0 / 0 / 5
Регистрация: 20.12.2016
Сообщений: 152
24.06.2017, 22:09  [ТС] 6
Цитата Сообщение от nd2 Посмотреть сообщение
Тут не указатель проверяется, а содержимое по указателю. И почему в конце массива указатель (адрес) будет равен нулю?
я вот тут тоже не очень понял (while *p)
колмпилятор выдает
1092702417
0
4197213
0
1
0
12 / 12 / 10
Регистрация: 04.06.2017
Сообщений: 99
24.06.2017, 22:14 7
Цитата Сообщение от swswsss Посмотреть сообщение
колмпилятор выдает
он выдает случайные числа
На студии 2017 все работает
0
nd2
3438 / 2817 / 1249
Регистрация: 29.01.2016
Сообщений: 9,426
24.06.2017, 22:15 8
Цитата Сообщение от savenkodenys Посмотреть сообщение
На студии 2017 все работает
Всё - это что? Код, вообще, не о чём.
0
12 / 12 / 10
Регистрация: 04.06.2017
Сообщений: 99
24.06.2017, 22:24 9
Цитата Сообщение от nd2 Посмотреть сообщение
Тут не указатель проверяется, а содержимое по указателю. И почему в конце массива указатель (адрес) будет равен нулю?
Почему это проверяется адрес, если я использую раименование? Да и все работает, цикл прекращается, а это еще одно подтверждение что моя запись верна. Более того, у Страуструпа для копирования массива в другой используется следующая запись
C++
1
while(*q++=*p++);
И отдельно указывает, что не нужно делать проверку, достигли ли мы конца массива, так как выражение и так сравнивается с нулем. Я надеюсь со Страуструпом не будете спорить?

Добавлено через 5 минут
nd2, специально для Вас нашол. Откройте Страуструп Язык Программирования С++ стр. 168 и почитайте первое предложения.
0
0 / 0 / 5
Регистрация: 20.12.2016
Сообщений: 152
24.06.2017, 22:25  [ТС] 10
savenkodenys спасибо!
переделал чуть
не знаю насколько верно
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 <cstdlib>
using namespace std;
 
int fill(int* p,int a) 
{
    while (*p<=a) 
    {
        *p = rand();
        p++;
    }
   
}
 
int main()
{
    srand(time(0));
    int array[5];
    int *ptr = array;
    fill(array,5);
    for (int i = 0; i < 5; i++)
    {
        *ptr + i;
    }
    cout << *ptr;
 
}
0
nd2
3438 / 2817 / 1249
Регистрация: 29.01.2016
Сообщений: 9,426
24.06.2017, 22:29 11
Цитата Сообщение от savenkodenys Посмотреть сообщение
Почему это проверяется адрес, если я использую раименование?
Читать умеешь?
Цитата Сообщение от savenkodenys Посмотреть сообщение
когда указатель будет равен нулю, а это конец массива
Цитата Сообщение от nd2 Посмотреть сообщение
Тут не указатель проверяется, а содержимое по указателю.
Цитата Сообщение от savenkodenys Посмотреть сообщение
когда указатель будет равен нулю, а это конец массива
Цитата Сообщение от nd2 Посмотреть сообщение
И почему в конце массива указатель (адрес) будет равен нулю?
Цитата Сообщение от savenkodenys Посмотреть сообщение
Я надеюсь со Страуструпом не будете спорить?
За Страуструпом не прячься. Разговор о твоём коде.
Цитата Сообщение от nd2 Посмотреть сообщение
Код, вообще, не о чём.
0
nd2
3438 / 2817 / 1249
Регистрация: 29.01.2016
Сообщений: 9,426
24.06.2017, 22:32 12
Цитата Сообщение от savenkodenys Посмотреть сообщение
На студии 2017 все работает
Вот результат работы.
Миниатюры
Функция: заполнить массив случайными значениями (с использованием указателей)  
0
nd2
3438 / 2817 / 1249
Регистрация: 29.01.2016
Сообщений: 9,426
24.06.2017, 22:35 13
А, давай код вот так изменим, и посмотрим работу:
C++
1
2
3
4
5
6
7
8
9
int fill(int* p) 
{
    while (*p) {
        *p = rand();
        cout << *p << endl;
        p++;
    }
    return *p;
}
Не слишком много значений для массива из пяти элементов?
Миниатюры
Функция: заполнить массив случайными значениями (с использованием указателей)  
0
12 / 12 / 10
Регистрация: 04.06.2017
Сообщений: 99
24.06.2017, 22:41 14
swswsss, вот вариант, который в точности вы и просили
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 <cstdlib>
#include <ctime>
 
void fill(int* p, const int size) {
    while (*p != size) {
        *p = rand();
        p++;
    }
}
 
int main()
{
    srand(time(0));
 
    const int size = 3;
    int mass[size];
    
    fill(mass, size);
    int *ptr = mass;
    
    for (int i = 0; i < size; i++)
        std::cout << *(ptr + i) << std::endl;
 
    system("pause");
    return 0;
}
0
nd2
3438 / 2817 / 1249
Регистрация: 29.01.2016
Сообщений: 9,426
24.06.2017, 22:43 15
Цитата Сообщение от savenkodenys Посмотреть сообщение
вот вариант, который в точности вы и просили
Опять не о чём. Бред.
0
0 / 0 / 5
Регистрация: 20.12.2016
Сообщений: 152
24.06.2017, 22:45  [ТС] 16
я извиняюсь заранее возможно за глупый вопрос подскажите почему указатель*p не используется в int main ? а создается новый *ptr и используется он же
0
12 / 12 / 10
Регистрация: 04.06.2017
Сообщений: 99
24.06.2017, 23:04 17
Цитата Сообщение от swswsss Посмотреть сообщение
*ptr + i;
обязательно нужно писать так
C++
1
*(ptr+i)
Иначе вы просто прибавите i к значению на которое ссылается ptr (указатель). Указатель это просто адрес числа, функции, обьекта класса и т.д. Сейчас попробую пояснить. Обьявим целочисленный указатель
C++
1
int *p;
Указатель должен куда-то ссылаться, в нашем случае на целочисленный тип данных. Это может быть просто число, тогда
C++
1
2
int a = 5;
p = &a;
или целочисленный массив, тогда мы указателю передаем адрес первого элемента массива
C++
1
2
3
int mass[3];
p = &mass[0];  // Явно
p = mass;  // Неявно
Можно посмотреть адрес
C++
1
cout << p << endl;
Если хотите посмотреть значение, то нужно, так сказать, разименовать указатель (поставить * перед ним)
C++
1
cout << *p << endl;
Если хотите узнать чему равен 3-ий элемент массива, то
C++
1
cout << *(p+2) << endl;
Смысл в том, что р ссылается на первый элемент массива. Если вы прибавите к р единицу, то он будет ссылаться уже на второй элемент того же массива. Ну и т.д. Думаю немножко станет яснее

Добавлено через 8 минут
Цитата Сообщение от swswsss Посмотреть сообщение
я извиняюсь заранее возможно за глупый вопрос подскажите почему указатель*p не используется в int main ? а создается новый *ptr и используется он же
Дело в области видимости переменных. Если переменная, ну или указатель, обьявлен и определен в фигурных скобках {}. То по выходу из них, программа не будет ничего знать и твоей переменной. Приведу яркий пример
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
#include <iostream>
 
int up(int x){
x = x + 2;
return x;
}
 
int main()
{
int x = 1;
up(x);
std::cout << x << std::endl;
system("pause");
return 0;
}
Можете вставить код и скомпилировать. И увидите, что функция up не будет менять значение х. Потому что, функция создает переменную, которая храниться по другому адресу, несмотря на одно и тоже значение.

Добавлено через 4 минуты
Цитата Сообщение от nd2 Посмотреть сообщение
Опять не о чём. Бред.
А слабо пояснить почему? С первым вариантом согласен. Там сравнение было небезопасным. Он работал, потому что массив не был инициализирован, то есть ему присвоили левые числа, среди которых не было нуля. Конечно, если все элементы массива инициализировать нулем, то функция ничего не сделать. Согласен. Но чем плох второй вариант?
0
nd2
3438 / 2817 / 1249
Регистрация: 29.01.2016
Сообщений: 9,426
24.06.2017, 23:09 18
Цитата Сообщение от savenkodenys Посмотреть сообщение
Но чем плох второй варинт?
Тем же, чем и первый: выходом за границу выделенной памяти. Из-за того, что *p никак не связано с size. Сравнение, в параметрах while(), не имеет никакого смысла. Чистое UB.

Добавлено через 2 минуты
Сделай вывод в fill(), и всё станет видно.
0
12 / 12 / 10
Регистрация: 04.06.2017
Сообщений: 99
24.06.2017, 23:11 19
Цитата Сообщение от nd2 Посмотреть сообщение
Тем же, чем и первый: выходом за границу выделенной памяти. Из-за того, что *p никак не связано с size. Сравнение, в параметрах while(), не имеет никакого смысла.
Вот дурья бошка И вправду чушь написал. Ну тогда самое простое, что приходит в голову
C++
1
2
3
4
5
for(int i = 0; i < size; i++)
{
*p = rand();
p++;
}
Теперь ведь верно, да?
0
nd2
3438 / 2817 / 1249
Регистрация: 29.01.2016
Сообщений: 9,426
24.06.2017, 23:13 20
Цитата Сообщение от savenkodenys Посмотреть сообщение
Теперь ведь верно, да?
Теперь - да.
0
24.06.2017, 23:13
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
24.06.2017, 23:13
Помогаю со студенческими работами здесь

Заполнить массив случайными значениями
Не могу найти ошибку, нужно заполнить массив из 12 элементов случайными не дублирующимися...

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

Заполнить массив С(10) случайными значениями
Заполнить массив С(10) случайными значениями. Организовать вывод на экран. Присвоить указателю...

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


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

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