Gå til innhold

Trekke variabler utenfor metode


Anbefalte innlegg

Jeg har nå følgende for å generere tilfeldige tall.

#include <boost/random.hpp>
#include <time.h>

using namespace boost;

double SampleNormal (double mean, double sigma) {
       mt19937 rng;                            // select random number generator
       rng.seed((unsigned int) time(0));       // seed generator with #seconds since 1970
       // select desired probability distribution
       normal_distribution<double> norm_dist(mean, sigma);
       // bind random number generator to distribution, forming a function
       variate_generator<mt19937&, normal_distribution<double> >  normal_sampler(rng, norm_dist);
       // sample from the distribution
       return normal_sampler();
}

 

Dette fungerer fint, hvis jeg ikke kaller metoden oftere enn én gang pr sekund. I så fall blir den randomiserte generatoren "seedet" med samme seed, og metoden returnerer like tall.

 

Jeg ønsker noe sånt som dette

#include <boost/random.hpp>
#include <time.h>
bool init = false;
variate_generator<mt19937&, normal_distribution<double> >  normal_sampler();

using namespace boost;
void Init(double mean, double sigma){
       mt19937 rng;                            // select random number generator
       rng.seed((unsigned int) time(0));       // seed generator with #seconds since 1970
       // select desired probability distribution
       normal_distribution<double> norm_dist(mean, sigma);
       // bind random number generator to distribution, forming a function
       variate_generator<mt19937&, normal_distribution<double> >  normal_sampler(rng, norm_dist);
       init = true;
}

double SampleNormal (double mean, double sigma) {
       if (!init)
             Init(mean, sigma);

       return normal_sampler();
}

 

Dette kompilerer ikke. Jeg vil altså deklarere metoden normal_sampler i Init() og referere den fra SampleNormal(). Hvordan løses dette?

Endret av buskmann
Lenke til kommentar
Videoannonse
Annonse
double SampleNormal (double mean, double sigma) {

  static variate_generator<mt19937&, normal_distribution<double>>* sampler = 0;

  if (!sampler) {

      // select random number generator

      mt19937 rng;                           

      rng.seed((unsigned int) time(0));      // seed generator with #seconds since 1970

      // select desired probability distribution

      normal_distribution<double> norm_dist(mean, sigma);

      // bind random number generator to distribution, forming a function

      sampler = new variate_generator<mt19937&, normal_distribution<double> >(rng, norm_dist);

  }

 

  return (*sampler)();

}

 

Memoryleak burde ikke være noe problem, siden det er kontrollert.

Endret av hishadow
Lenke til kommentar

Den løsningen fungerer heller ikke, dvs at den kompilerer, men den gir merkelige resultater.

 

Har nå denne koden:

#include <boost/random.hpp>
#include <time.h>
#include <conio.h>

using namespace boost;

double SampleNormal (double mean, double sigma) {
 static variate_generator<mt19937&, normal_distribution<double> >* sampler = 0;
 if (!sampler) {
     // select random number generator
     mt19937 rng;
     rng.seed((unsigned int) time(0));      // seed generator with #seconds since 1970
     // select desired probability distribution
     normal_distribution<double> norm_dist(mean, sigma);
     // bind random number generator to distribution, forming a function
     sampler = new variate_generator<mt19937&, normal_distribution<double> >(rng, norm_dist);
 }

 return (*sampler)();
}

int main(int argc, char* argv[])
{
  while (getch())
     std::cout << SampleNormal(8,1) << std::endl << std::flush;
}

 

Det kommer plausible tall til å begynne med, men så starter den å bytte på mellom to verdier. Prøv selv med vedlagte fil (Windows, rename til .exe).

Normal.doc

Lenke til kommentar
Den løsningen fungerer heller ikke, dvs at den kompilerer, men den gir merkelige resultater.

 

Det kommer plausible tall til å begynne med, men så starter den å bytte på mellom to verdier. Prøv selv med vedlagte fil (Windows, rename til .exe).

Prøv denne:

double SampleNormal (double mean, double sigma) {

  static variate_generator<mt19937&, normal_distribution<double> >* sampler = 0;

      if(!sampler) {

        // select random number generator

        mt19937* rng = new mt19937();

        // seed generator with #seconds since 1970

        rng->seed((unsigned int) time(0));

        // select desired probability distribution

        normal_distribution<double>* norm_dist = new normal_distribution<double>(mean, sigma);

        // bind random number generator to distribution, forming a function

        sampler = new variate_generator<mt19937&, normal_distribution<double> >(*rng, *norm_dist);

      }

 

  return (*sampler)();

}

variate_generator bruker visst referanser i konstruktøren, så det gikk ikke så bra med lokale variabler. Endret litt.

 

ed: fikk ikke åpnet doc'en din.

test.doc

Endret av hishadow
Lenke til kommentar
Memoryleak burde ikke være noe problem, siden det er kontrollert.

4992738[/snapback]

 

Hvorfor er ikke dette noe problem, hva betyr det at det er "kontrollert"?

5009766[/snapback]

Mener å vite at det vil bli frigjort når programmet avsluttet. Siden det bare allokeres en gang ved starten, vil det være en "kontrollert" memoryleak. I motsetning til en ukjent memoryleak som kan akkumuleres under programkjøring.

Lenke til kommentar

Du vil nok få rapport om memory leak dersom du ikke deleter dynamisk allokert minne. Dessuten er det dårlig skikk å deallokere minnet du har brukt. Kontrollert eller ikke kontrollert, så har alltid programmet ditt ansvar for minnet det bruker.

 

 

[EDIT] Leif was here

Endret av Nazgul
Lenke til kommentar

Opprett en konto eller logg inn for å kommentere

Du må være et medlem for å kunne skrive en kommentar

Opprett konto

Det er enkelt å melde seg inn for å starte en ny konto!

Start en konto

Logg inn

Har du allerede en konto? Logg inn her.

Logg inn nå
  • Hvem er aktive   0 medlemmer

    • Ingen innloggede medlemmer aktive
×
×
  • Opprett ny...