Mam takie zadanko:
Wylosuj p ε {-100, 100}. Następnie losuj liczby z tego
samego przedziału, dopóki nie wypadnie ta sama liczba
Przykład:
Podaj p: 100
Liczba prób, po których znów wylosowano 100: 7
Pomógłby mi ktoś jak to napisać?
Mam takie zadanko:
Wylosuj p ε {-100, 100}. Następnie losuj liczby z tego
samego przedziału, dopóki nie wypadnie ta sama liczba
Przykład:
Podaj p: 100
Liczba prób, po których znów wylosowano 100: 7
Pomógłby mi ktoś jak to napisać?
Pewnie, bardzo chętnie pomagamy na forum. Z czym masz problem?
Potrzebujesz dwóch rzeczy: losowania liczb (na dole czytelny przykład), oraz jakiegoś ich spamiętywania (by wiedzieć, czy już trafiłeś jakąś, czy nie) — narzucające się rozwiązania to tablica booli (preferowane) lub unordered_set
.
Mianowicie z wylosowaniem liczby z danego przedziału i dopisanie do zmiennej próby żeby wylosowana liczba była równa podanej
Mianowicie z wylosowaniem liczby z danego przedziału […]
To podany przeze mnie link ma ładny i czytelny przykład na dole.
[…] dopisanie do zmiennej próby żeby wylosowana liczba była równa podanej
A tego zdania nie rozumiem…
@Althorion: Chciałbym to zrobić pętlą do while czyli dodaj 1 do zmiennej int proby jeżeli wylosowana liczba nie jest równa tej podanej
Mhm. Brzmi jak rozwiązanie. Zatem w czym tkwi problem?
Jak konkretnie zrobić losowanie z przedziału (-100, 100)
#include <iostream>
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
using namespace std;
int liczba;
int proby;
int los;
int main ()
{
cout << "Podaj p: ";
cin >> liczba;
los = (rand() % 100) + (-100);
do {
++proby;
}while(los != liczba);
cout << "Liczba " << proby << endl;
}
Poprawisz kod na poprawny?
Jak próbujesz implementować tak jak w tym linku, to jakie problemy napotykasz? Coś Ci się nie kompiluje (jaki kod? Z jakim błędem?), daje zły rezultat (jaki kod? Jaki rezultat?), coś jeszcze innego?
Niestety nie sposób Ci pomóc, jeśli nie wiemy, z czym dokładnie sobie nie radzisz.
A, w sumie mogę poprawić — wywal biblioteki z C (w końcu piszesz w C++), tzn. stdio.h
, stdlib.h
, time.h
; przerzuć zmienne globalne liczba
, proby
, los
do środka main
(niewielka poprawka, ale zawsze…) i skorzystaj z ww. metody.
Ostatecznie otrzymasz coś z grubsza takiego:
#include <iostream>
#include <random>
using namespace std;
int main()
{
int liczba;
int proby = 0;
int los;
cout << "Podaj p: ";
cin >> liczba;
std::random_device rd;
std::mt19937 gen(rd());
std::uniform_int_distribution<> distrib(-100, 100);
do {
++proby;
los = distrib(gen);
} while (los != liczba);
cout << "Liczba " << proby << endl;
return 0;
}
Nie mam kompilatora pod ręką, ale wygląda na działające — celowo wprowadzałem możliwie minimalne zmiany.
Najistotniejszą zmianą jest zastanowienie się ile razy chcesz losować wartość, bo twój obecny kod robi to raz.
@Althorion: Wszystko super działa, ale czy mógłbyś ten kod tak napisać, żeby nie używać random_device itp tylko srand i przedział typu if(liczba >= -100 && liczba <= 100) {...}
Nie — powołuję się na klauzulę sumienia, zabraniającej mi celowego pisania złego kodu¹. Ale jeśli chcesz to samemu naprawić, to już Ci razem z AnyKtokolwiek napisaliśmy w komentarzu pod postem, jakie błędy popełniasz.
¹ Ten kod jest zły z wielu powodów, a przede wszystkim dlatego, że ma nierównomierny rozkład wartości.
Dlaczego koniecznie chcesz używać niezalecanego rozwiązania?
Bo mam to robić za pomocą poznanych metod, ale no nic, dzięki.
Czy masz zakaz nauki na własną rękę? Bo wiesz, to nic trudnego przeczytać kawałek dokumentacji podlinkowany przez @Althorion kilkukrotnie i poznać poprawniejsze metody.
@kq: Sprawa wygląda w ten sposób, że piszę w innym języku. Dostałem takie zadanie ze szkoły i mam to zrobić poznanymi metodami, ale to w sumie już nie ważne jakoś sobie poradzę
W jakim innym języku? Jak nie C++ to trzeba było zadać pytanie odnośnie danego języka.
Nadal nie rozumiem dlaczego nie chcesz poznać poprawnej metody i tą poznaną metodą rozwiązać zadania.
W czym nie rozumiesz tego, że nie mogę używać innych metod niż tych poznanych? Tak po prostu jest i tyle
#include <iostream>
#include <stdlib.h>
using namespace std;
int main ()
{
int value,count;
while((cout<<"Podaj p: ")&&(cin>>value)&&(-100<=value)&&(value<=100)) {}
for(count=0;value!=rand()%201)-100';++count) {}
cout<<"Liczba "<<count<<endl;
return 0;
}
@Kuba Wąsowicz:
Rozwiązania które tu dostałeś są lepsze niż użycie funkcji rand "odziedziczonej" z języka C, ale... Uczę od wielu lat podstaw programowania i rozumiem dlaczego wolisz zacząć od rand() [1] ;)
No to krótki tutorial na temat rand() - skoro już musisz go używać to przynajmniej zrób to świadomie ;)
Funkcja rand() zwraca Ci wartość pseudolosową z zakresu od zera do pewnej stałej RAND_MAX (jest to wartość zależna od kompilatora i/lub systemu operacyjnego i nie masz na nią absolutnie żadnego wpływu). Najprostszym [2] sposobem na "zamianę" zakresu 0....RAND_MAX na zakres A...B (przy założeniu, że A<B<RAND_MAX) jest wykonanie dwóch prostych operacji.
Zacznijmy od takiego wyrażenia
rand() % (M+1)
Jeśli weźmiesz wartości z zakresu 0....RAND_MAX i dla każdej z nich policzysz resztę z dzielenia przez M+1
, to dostaniesz wartości z zakresu 0.....M [3]
rand() % (M+1) + A
Miałeś wartości z zakresu 0...M, dodajesz do nich A - dostaniesz zakres A....A+M
Pytanie - ile powinna wynosić wartość "M" abyś uzyskał zakres A....B ?
B = A+M --> M = B - A
Czyli ostatecznie - takie wyrażenie pozwoli Ci wylosować wartość z zakresu od A do B:
rand() % (B-A + 1) + A
[1]
Natomiast absolutnie nie rozumiem podejścia prowadzącego/nauczyciela, który zabraniałby uzycia lepszego rozwiązania
[2]
Z wielu powodów wcale nie najlepszym...
[3]
Tu od razu widać pierwszy problem z tym podejściem - niektóre wartości po policzeniu modulo będą pojawiać się częściej niż inne
@Bartłomiej Golenko apropos rzutu kostką
#include <ctime>
#include <iostream>
using namespace std;
int main()
{
srand(time(0));
int have=9999;
while(true)
{
int myBid=1;
if(myBid==1+rand()%6) have+=6;
else --have;
cout<<"\r"<<have<<' ';
}
return 0;
}