Консультация № 198402
27.04.2020, 01:04
0.00 руб.
0 3 0
Уважаемые эксперты! Пожалуйста, ответьте на вопрос:
как в этой программе работает задание вероятности и цикл, где вызывается выстрел




Приложение:
//Программно промоделировать стрельбу по мишени группой человек.
//Каждый человек (абстрактный класс Person) имеет свое имя, возраст (в годах) и стаж обучения стрельбе (в годах).
//Люди делятся на новичков, опытных и ветеранов (потомки класса человек).
//Для каждого человека определите полиморфный метод.
//«Стрелять» без параметров, возвращающих логическое значение (попал – true, не попал – false).
//Попадание определяется случайным образом,
//причем для новичка вероятность попасть равна 0,01*стаж обучения;
//для опытного = 0,05*стаж обучения стрельбе; для ветерана = 0,9 – 0,01*возраст.
//Люди стреляют по очереди, начиная с первого, пока кто-то не попадет в мишень.
//Стрельба прекращается после того, как кто-то попал или все выстрелили по одному разу.
//После каждого выстрела нужно выводить на экран всю информацию о стреляющем и результат стрельбы.
//В главной программе создайте массив из 5 людей в таком порядке:
//новичок, опытный, ветеран, опытный, новичок и произведите стрельбу с выводом ее результатов.


#include <ctime>
#include <iostream>
#include <random>
#include <string>
#include <vector>

//абстрактный класс человек, создаём для наследования в производные характеристик
class Person
{
//блок переменных private
std::string name;
int age;
//блок под наследование
protected:
//конструктор с параметрами
Person
(std::string name,int age)
{this-> name = name ;
this->age = age ;}
//виртуальный метод вывод информации
virtual
void print_data() const
{
std::cout<<"name\t\t: "<<name<<std::endl<<"age\t\t: "<<age<<std::endl;
}
//метод возраст
int get_age() const
{
return age;
}

};
//класс стрелок, наследник класса Person
class SHOOTER : public Person
{
//private-переменная опыт
int experience;

public:
//конструктор класса SHOOTER
SHOOTER
( std::string const & name, int age,int experience):Person(name,age){this->experience=experience;}
//метод опыт стрелка
int get_experience() const
{
return experience;
}
//метод выстрел
bool successfully_shot() const
{
return sucsess_probability(probability());
}
virtual
//виртуальный метод вывод опыта и вероятности(переопреелённый для класса стрелок)
void print_data() const override
{
Person::print_data();
std::cout
<<"experience\t: "<<experience<<std::endl<<"p = "<<probability()<<std::endl;
}
private:
//метод стрельба
virtual
double probability() const=0;
bool sucsess_probability(double probability) const
{//генератор случайных(вихрь мерсена)
static std::mt19937 gen( unsigned(time(0)) );
//Формируем распределение целых чисел с одинаковыми интервалами и вероятностью в каждом интервале
std::discrete_distribution<>distr( { 1 - probability, probability});
return distr( gen );
}
};
//класс новичок-наследник стрелка
class BEGINNER : public SHOOTER
{
public:
using SHOOTER::SHOOTER;
//переопределяем функции
virtual
void print_data() const override
{
std::cout << "beginner_shooter" << std::endl;
SHOOTER::print_data();
}
//переопределяем вероятность
virtual
double probability() const override
{
return 0.01*get_experience();
}
};
//класс опытный
class EXPERIENCED : public SHOOTER
{
public:
using SHOOTER::SHOOTER;
virtual
double probability() const override
{
return 0.05*get_experience();
}
virtual
void print_data() const override
{
std::cout << "experienced_shooter"<< std::endl;
SHOOTER::print_data();
}
};
//класс ветеран
class VETERAN : public SHOOTER
{
public:
using SHOOTER::SHOOTER;
virtual
double probability() const override
{
return 0.9-0.01*get_age();
}
virtual
void print_data() const override
{
std::cout << "veteran_shooter"<< std::endl;
SHOOTER::print_data();
}
};
typedef std::vector < SHOOTER*> SHOOTER_ptrs;//делаем псевдоним для vector<SHOOTER*>
int main()
{
SHOOTER_ptrs shooter_ptrs;//массив стрелков(вектор)
//1 стрелок
shooter_ptrs.push_back ( new BEGINNER ("Кравчук",80,20));
//2 стрелок
shooter_ptrs.push_back (new EXPERIENCED ("Кучма",50,10));
//3 стрелок
shooter_ptrs.push_back (new VETERAN ("Ющенко",45,50));
//4 стрелок
shooter_ptrs.push_back (new EXPERIENCED ("Янукович",60,20));
//5 стрелок
shooter_ptrs.push_back (new BEGINNER ("Порошенко",55,70));
//Стрельба
std::cout<<std::endl<<std::endl;
int shots_count{};//cчетчик
for( auto shooter_ptr:shooter_ptrs )//проходимся по всем 1 раз
{
std::cout << "# "<< ++shots_count<< ":"<< std::endl;
shooter_ptr->print_data();
auto
res=shooter_ptr->successfully_shot();
std::cout<<"result\t\t: "<<res<< std::endl<< std::endl;
if( res )
{
break;
}
}
system("pause");
}

Обсуждение

давно
Академик
20764
1861
27.04.2020, 12:18
общий
а где rand()? как результат одной попытки задаётся?
давно
Посетитель
403950
1
27.04.2020, 22:13
общий
[q=20764][/q]
да
давно
Советник
400484
472
28.04.2020, 12:45
общий
Добрый день.
В классе SHOOTER заданы функция стрельбы:
Код:

class SHOOTER : public Person
{
...
//метод выстрел
bool successfully_shot() const
{
return sucsess_probability(probability());
}
...
private:
//метод стрельба
virtual double probability() const = 0;
bool sucsess_probability(double probability) const
{
//генератор случайных(вихрь мерсена)
static std::mt19937 gen(unsigned(time(0)));
//Формируем распределение целых чисел с одинаковыми интервалами и вероятностью в каждом интервале
std::discrete_distribution<>distr({ 1 - probability, probability });
return distr(gen);
}
};

Вероятности для выстрела задаются в уровне пользователя. Рассмотрим на примере класса VETERAN
Код:

class VETERAN : public SHOOTER
{
public:
...
virtual double probability() const override
{
return 0.9 - 0.01*get_age();
}
...
};

Вероятность будет равна 0.9-0.01*(на возраст стрелка). Соответственно для 30 летнего будет: 0.9-0.01*30 = 0,6, а для новорожденного (0 лет) равна 0.9.
Цикл стрельбы прописан тут:
Код:

for (auto shooter_ptr : shooter_ptrs)//проходимся по всем 1 раз
{
std::cout << "# " << ++shots_count << ":" << std::endl;
shooter_ptr->print_data();
auto res = shooter_ptr->successfully_shot();
std::cout << "result\t\t: " << res << std::endl << std::endl;
if (res)
{
break;
}
}


Вам еще нужно почитать про виртуальные функции. Посмотрите тут.
Код:

virtual void print_data() const override

Вы в одной функции и делаете ее виртуальной и переопределяете. Странно как-то...
Форма ответа