random_device()() work only for initializing data members - c++11

This is typical sequence of declarations/definitions for generating random numbers in C++11:
std::random_device rd
std::default_random_engine gen(rd());
std::uniform_int_distribution<> dist(1, 6);
rd is only used for seeding the generator gen, so I am thinking of not defining it in particular. In stead, I would like to use a temporary for this purpose:
int main() {
std::default_random_engine gen(std::random_device()());
std::uniform_int_distribution<> dist(1,6);
}
But compiler gave me an error:
function returns function
But this works if I initialize the engine as a data member:
class A
{
public:
A();
private:
std::default_random_engine gen;
std::uniform_int_distribution<> dist;
}
A::A() : gen(std::random_device()()), dist(1) {}
So why can I not use std::random_device()() in normal statement to initialize a random generator but can use it in initializing data members? How to make it working in normal statement? Thanks.
PS: I am working on Windows 10 using Visual Studio 2015.

Related

Default constructor setting random value

I'm writing a simple class for atoms objects. Here's what I've written so far:
#include <random>
class Atom {
int mSpin;
public:
Atom();
Atom(int);
Atom(const Atom&);
~Atom() {}
Atom& operator= (const Atom &atom);
};
And the .cpp file:
include "Atom.h"
Atom::Atom() {
}
Atom::Atom(int spin) : mSpin(spin) {}
Atom::Atom(const Atom& copy) : mSpin(copy.mSpin) {}
/* OPERATORS */
Atom& Atom::operator= (const Atom &copy) {
mSpin = copy.mSpin;
return *this;
}
I want to make the default constructor such that when I'm creating an object, mSpin will be randomly set as 1 or -1. I understand how to do it with rand() but rand() is not very good and I'd like to use . I'm kind of confused by the use of , even after reading the documentation and other answers on here.
Usually I'd do something like this:
#include <random>
std::random_device rd;
std::mt19937 gen(rd());
std::uniform_int_distribution<> dis(0,1);
int random_number = dis(gen);
but I'm not sure how to use it inside a class. I tried placing it inside the default constructor but I think it's wrong because it would seed each time I create an atom?
Hope the question is clear.
You should make the random device and generator static members of the Atom class. This way, like global variables, they are initialized only once for the duration of your program.
class Atom {
// declaration
static std::random_device rd;
static std::mt13397 gen;
...
};
// definition - this must be in Atom.cpp
std::random_device Atom::rd;
std::mt13397 Atom::gen(Atom::rd());
You can delegate to a function in the cpp file:
namespace {
random_device rd;
mt19937 gen(rd());
uniform_int_distribution<> dis(0,1);
}
int spin() {
return dis(gen) == 0 ? -1 : 1;
}
Delete your implementation of the default CTOR.
And to follow the rule 'initialise all variables' change Atom.hpp:
int spin(); // Return -1 or 1, randomly
class Atom {
int mSpin = spin();
public:
Atom() = default;
...
};
Then, in your cpp file, delete your Atom default CTOR implementation and move 'spin' function definition out of the anonymous namespace.

C++11 container of borrowed unique_ptrs

I have a vector of unique_ptrs and want to filter it into a new vector of the same type.
vector<unique_ptr<Thing>> filter_things(const vector<unique_ptr<Thing>> &things) {
vector<unique_ptr<Thing>> things;
// i want the above line to be something like: vector<const unique_ptr<Thing> &>
// but I don't think this is valid
for (const unique_ptr<Thing> &thing : things) {
if (check(thing)) {
filtered.push_back(thing); // this part shouldn't work since it
// would duplicate a unique_ptr
}
}
return filtered;
}
I want the caller to maintain ownership of all the Things. I want the return value of this function to be purely read only (const), and I don't want to make copies as it is very expensive to copy a Thing.
What is the best way to accomplish this?
Is this possible with unique_ptrs?
In some sense, we are creating multiple references by returning a new vector of references, so unique_ptr may not make sense. However, it is purely read only! So there should be some way to make this work. The lifetime of ``things'' is guaranteed to be larger than the filtered things.
Note that the caller owns the parameter supplied.
You can use reference_wrapper from <functional>
#include <memory>
#include <functional>
#include <vector>
#include <iostream>
using namespace std;
struct Thing {};
using PThing = unique_ptr<Thing>;
using RefThing = reference_wrapper<const PThing>;
vector<RefThing> filter_things( const vector<PThing>& things )
{
vector<RefThing> filtered;
int i = 0;
for( auto&& thing : things )
{
if( i++%2 )
filtered.push_back( ref(thing) );
}
return filtered;
}
int main()
{
vector<PThing> vec;
vector<RefThing> flt;
vec.resize(25);
flt = filter_things(vec);
cout << flt.size() << endl;
}
If what you want is getting a filtered set of element not an actual container containing them, boost::range can be a good solution.
auto filtered_range(const std::vector<std::unique_ptr<Thing>> &things) {
return things | boost::adaptors::filtered([](const auto& thing) {
return check(thing);
});
}
I used some of c++14 syntax but I don't think it's hard to make it to c++11.
You can use it like this.
std::vector<std::unique_ptr<Thing> > things;
for(const auto& thing : filtered_range(things)) {
// do whatever you want with things satisfying 'check()'
}
One of disadvantages is that the range itself is not a container so if you traverse the range more than once, every 'thing' will be checked if it satisfies check().
If a container storing the checked things AND controlling the lifetime of things are what you really want, I would prefer using std::vector<std::shared_ptr<Thing> > and returning std::vector<std::weak_ptr<Thing> >. You can check if it's really one and the only ptr to a thing with std::shared_ptr::unique() before deleting it from things.

c++ assign a class member function a lambda function for computation efficiency [duplicate]

This question already has answers here:
C++ lambda with captures as a function pointer
(9 answers)
Closed 7 years ago.
UPDATED: (Rephrased). I'm looking to boost the computation efficiency of my code by make an run-time assignment of a class member function to one of many functions conditional on other class members.
One recommended solution uses #include <functional> and function<void()>, as shown in the simple test example:
#include <iostream>
using namespace std;
struct Number {
int n;
function(void()) doIt;
Number(int i):n(i) {};
void makeFunc() {
auto _odd = [this]() { /* op specific to odd */ };
auto _even = [this]() { /* op specific to even */ };
// compiles but produces bloated code, not computatinally efficient
if (n%2) doIt = _odd;
else doIt = _even;
};
};
int main() {
int i;
cin >> i;
Number e(i);
e.makeFunc();
e.doIt();
};
I'm finding that the compiled code (i.e. debug assembly) is grotesquely complicated and presumably NOT computationally efficient (the desired goal).
Does someone have an alternative construct that would achieve the end goal of a computationally efficient means of conditionally defining, at run-time, a class member function.
A capturing lambda expression cannot be assigned to a regular function pointer like you have.
I suggest using
std::function<void()> doIt;
instead of
void (*doIt)();

How to store functional objects with different signatures in modern C++

I would like to know if there is a way to store functional objects (functions, callbacks, ...) with different signatures in a standard container (std::map) with modern C++ only. The library that manages the container does not know which signatures will be used by its "clients".
My need is the same as exposed here : How to store functional objects with different signatures in a container?, and this solution https://stackoverflow.com/a/8304873/4042960 is about perfect for me: I would just like to do the same thing without boost. As far as I know, there is no std::any. The best solution for me would be to store std::function without specialized them, but I do not know how to do it, if it is possible.
Edit:
With the answers you give to me I wrote this example :
#include <map>
#include <memory>
#include <functional>
#include <string>
#include <iostream>
#include <stdexcept>
class FunctionMap
{
struct Base {
virtual ~Base() {}
};
template<class R, class... Args>
struct Func : Base
{
std::function<R(Args...)> f;
};
std::map<std::string, std::shared_ptr<Base> > _map;
public:
template<class R, class... Args>
void store(const std::string &key, const std::function<R(Args...)> &f) {
auto pfunc = std::make_shared<Func<R, Args...> >();
pfunc->f = f;
_map.insert(std::make_pair(key, pfunc));
}
template<class R, class... Args>
std::function<R(Args...)> get(const std::string &key) {
auto pfunc = std::dynamic_pointer_cast<Func<R, Args...> >(_map[key]);
if (pfunc)
return pfunc->f;
else
throw std::runtime_error("Bad type for function's parameters");
}
};
// test
int plus(int a, int b) { return a+b; }
double multiplies(double x, double y) { return x*y; }
int main()
{
FunctionMap fm;
fm.store("plus", std::function<int(int, int)>(&plus));
fm.store("multiplies", std::function<double(double, double)>(&multiplies));
// fm.store("square", std::bind(&multiplies, std::placeholders::_1, std::placeholders::_1));
std::cout << "5 + 3 = " << fm.get<int, int, int>("plus")(5, 3) << std::endl;
std::cout << "5 * 3 = " << fm.get<double, double, double>("multiplies")(5.0, 3.0) << std::endl;
return 0;
}
This works well, but I would like to improve it a bit:
1) I would like to be able to use std::bind : fm.store("square", std::bind(&multiplies, std::placeholders::_1, std::placeholders::_1)); but currently that does not compile ;
2) I would like to use fm.get<int (int, int)>("plus") instead of fm.get<int, int, int>("plus") but I do not know how to do it.
Many thanks for your help !
You can write your own any. Without all the compiler workarounds and stuff, boost::any can be written in about 30 lines of code.
Function objects are in no way different from any other kind of objects, so anything applicable to objects in general is applicable to function objects.
So you want to store different kinds of (function) objects in a map. This is normally done by storing (smart) pointers to a base class, where each derived class holds its own kind of objects you want to store.
struct Base {
virtual ~Base(){}
};
template <typename A>
struct Object : Base {
A value;
};
That's your basic caveman's boost::any. Your clients do something like this:
Base* b = mymap["foo"];
dynamic_cast<Object<void(*)(int)>*>(b)->val(123);
But with appropriate checks of course.

Speeding up std:.vector filling with new c++11 std::async

i'm using vc++ 2013 express edition.
I'm studying some new feature of c++11 like std::async, and std::future.
I have a class Foo, with an std::shared_ptr<std::vector<unsigned int> >.
In Foo ctor i use std::make_shared to allocate in the heap the vector;
From Foo.h
Class Foo{
public:
Foo();
private:
std::shared_ptr<std::vector<unsigned int> > testVector;
unsigned int MAX_ITERATIONS = 800000000;
void fooFunction();
}
From Foo.cpp
Foo::Foo(){
testVector = std::make_shared<std::vector<unsigned int> >();
//fooFunction(); this take about 20 sec
std::async(std::launch::async, &Foo::fooFunction, this).get(); // and this about the same!!
}
void Foo:fooFunction(){
for (unsigned int i = 0; i < MAX_ITERATIONS; i++){
testVector->push_back(i);
}
}
Th problem is i can't see any gain between calling std::async(std::launch::async, &Foo::fooFunction, this).get(); and fooFunction();
Why??
Any help will be appreciated.
Best regards
std::async returns a std::future.
Calling get() on the future will make it wait until the result is available, then return it. So, even if it is run asynchronously, you are doing nothing but waiting for the result.
std::async doesn't magically parallelize the for loop in Foo::fooFunction.

Resources