I'm confused about the for each loop in C++. I have this code in a main game loop:
for each (Bubble b in bubbles){
b.Update();
}
for each (Bubble b in bubbles){
b.Draw();
}
It doesn't update anything, but does draw 1 bubble.. What's wrong with it?
EDIT: This code works
struct BubbleUpdater {
void operator()(Bubble & b) { b.Update(); }
} updater;
struct BubbleDrawer {
void operator()(Bubble & b) { b.Draw(); }
} drawer;
void OnTimer(){ //this is my main game loop
std::for_each(bubbles.begin(),bubbles.end(),drawer);
std::for_each(bubbles.begin(),bubbles.end(),updater);
}
I had this problem as well in C#, it drove me crazy for a while. From what I found, the for each loop creates a new object for each object in your collection. So it's creating something by value, rather than by reference (if you used a standard for loop), which results in the original collection not being effected. I always found for each loops good for reading, but not for updating.
Change your BubbleUpdater class to accept it's argument by reference
struct BubbleUpdater {
void operator()(Bubble & b) { b.Update(); }
} updater;
With that, your call to std::for_each should work.
If your compiler supports it (and VC10 does), then you can use lambdas instead of creating a distant function object class. And yes, it's standard c++, or will be soon enough.
std::for_each (bubbles.begin(), bubbles.end(), [](Bubble & b){
b.Update();
});
That's not C++, it's a Qt extension from memory. The new C++0x for each loop will have the syntax
for(type identifier : expression)
that is,
for(auto x : std::string("ohai"))
However, in C++03 there is no dedicated for each loop language construct.
for each isn't valid c++, and if you were thinking of std::for_each() or BOOST_FOREACH they have different syntax.
std::for_each is a function and has the following interface:
std::for_each(InputIterator begin, InputIterator end, function f);
BOOST_FOREACH is a preprocessor macro and has the following interface:
BOOST_FOREACH(element e, container c)
{
do_thing(e);
e.whatever();
}
Related
CppCheck suggest me to replace one of my code by a STL algorithm, I'm not against it, but I don't know how to replace it. I'm pretty sure this is a bad suggestion (There is warning about experimental functionalities in CppCheck).
Here is the code :
/* Cutted beginning of the function ... */
for ( const auto & program : m_programs )
{
if ( program->compare(vertexShader, tesselationControlShader, tesselationEvaluationShader, geometryShader, fragmentShader) )
{
TraceInfo(Classname, "A program has been found matching every shaders.");
return program;
}
}
return nullptr;
} /* End of the function */
And near the if condition I got : "Consider using std::find_if algorithm instead of a raw loop."
I tried to use it, but I can't get the return working anymore... Should I ignore this suggestion ?
I suppose you may need to use that finding function not once. So, according to DRY, you need to separate the block where you invoke an std::find_if algorithm to a distinct wrapper function.
{
// ... function beginning
auto found = std::find_if(m_programs.cbegin(), m_programs.cend(),
[&](const auto& prog)
{
bool b = prog->compare(...);
if (b)
TraceInfo(...);
return b;
});
if (found == m_programs.cend())
return nullptr;
return *found;
}
The suggestion is good. An STL algorithm migth be able to choose an appropriate
approach based on your container type.
Furthermore, I suggest you to use a self-balancing container like an std::set.
// I don't know what kind of a pointer you use.
using pProgType = std::shared_pointer<ProgType>;
bool compare_progs(const pProgType &a, const pProgType &b)
{
return std::less(*a, *b);
}
std::set<std::shared_pointer<prog_type>,
std::integral_constant<decltype(&compare_progs), &compare_progs>> progs.
This is a sorted container, so you will spend less time for searching a program by a value, given you implement a compare operator (which is invoked by std::less).
If you can use an stl function, use it. This way you will not have to remember what you invented, because stl is properly documented and safe to use.
Think about this code in C/C++:
bool cond = true;
while(cond){
std::cout << "cond is currently true!";
}
Is it possible to create a function that can be called like this?
myFunction(some_parameters_here){
//Code to execute, maybe use it for callbacks
myOtherFunction();
anotherFunction();
}
I know you can use function pointers and lambda functions, but I was wondering if you can. I'm pretty sure there is a way to do so, because how would while() exist?
while(condition) { expression } is not a function but a control structure / a separate language construct; it executes expression again and again as long as condition evaluates to true (i.e. something != 0).
an function definition of the form void myFunction(int someParameter) { expression }, in contrast, is executed only when it is called by another function.
Hope it helps a bit;
Caution: this solution comes without the guarantee that your code reviewer will like it.
We can use a trick similar to the one Alexandrescu uses for his SCOPE_EXIT macro (awesome one-hour conference, this bit is at 18:00).
The gist of it: a clever macro and a dismembered lambda.
namespace myFunction_detail {
struct Header {
// Data from the construct's header
};
template <class F>
void operator * (Header &&header, F &&body) {
// Do something with the header and the body
}
}
#define myPrefix_myFunction(a, b, c) \
myFunction_detail::Header{a, b, c} * [&]
Using it as follows:
myPrefix_myFunction(foo, bar, baz) {
}; // Yes, we need the semicolon because the whole thing is a single statement :/
... reconstitutes a complete lambda after macro expansion, and lands into myFunction_detail::operator* with acess to foo, bar, baz, and the body of the construct.
E.g. a class Unit has three functions:
class Unit{
void StandUp();
void SitDown();
void Die();
}
I have a list of pointers list<Unit*> UnitList;
When I want everyone to stand up:
void EveryoneStandUp(){
for(list<Unit*> it = UnitList.begin(); it != UnitList.eng(); it++){
(*it)->StandUp();
}
}
Now if I want everyone to SitDown, I would copy the code above and change StandUp() to SitDown(). For every new function I write, if I want everyone to do it, I have to have another for-loop body in my code.
Is it possible to put this for-loop body in another function, which I can reuse whenever I want to call a certain function from all of the members in the UnitList?
I feel like this must have answers somewhere else, I tried googling but have little idea which keywords I should look for. Thanks for answers!
You may do:
void Everyone(void (Unit::*method)())
{
for (std::list<Unit*>::iterator it = UnitList.begin(); it != UnitList.end(); it++){
((*it)->*method)();
}
}
And call it
Everyone(&Unit::StandUp);
but in c++11, your example may be rewritten as:
for (auto* unit : UnitList) {
unit->StandUp();
}
which seems clear enough.
you can use c++ algorithms available,
http://www.cplusplus.com/reference/algorithm/for_each/
It can be solved by having a helper function, which does the actual looping and have the member function to be called as an argument.
Something like this:
void UnitHelperFunction(void (Unit::*func)())
{
for (...)
{
((*itr)->*func)();
}
}
void EveryoneStandUp()
{
UnitHelperFunction(&Unit::StandUp);
}
I can't seem to find any relevant information on the following sort of thing.
Say that you have a program with numerous methods (for example, a custom set of tests).
How could you loop through them based on something like the following pseudo-code
for(int i= 0; i < 10 ; i ++)
{
function(i)();
}
so that it will go through this loop and therefore launch methods function0, function1, function2, function3, function4, function5, function6, function7, functuin8, function9.
If there are ways to also do this in C# or Java, then information for them also would be appreciated.
In C++, the only way I can think of is to use of an array of function pointers. See here.
For Java, which supports Reflection, see this. And for C#, which also supports Reflection, this.
The language feature you would need for this is called "Reflection", which is a feature C++ does not have. You will need to explicitly name the functions you want to call.
Well, if you have an array of function pointers, you can do something like this:
void (*myStuff[256])(void);
And then when you want to call each function just dereference each of them as you iterate.
Keep in mind that every function in your array must have the same parameter signature and return type.
Here's a solution using Boost.Function and Boost.Bind in which the loop doesn't need to worry about the parameter signatures of the functions you are calling (I haven't tested it in a compiler, but I have very similar code in a project which I know works):
#include <vector>
#include <boost/function.hpp>
#include <boost/bind.hpp>
using std::vector;
using boost::function;
using boost::bind;
void foo (int a);
void bar (double a);
void baz (int a, double b);
int main()
{
// Transform the functions so that they all have the same signature,
// (with pre-determined arguments), and add them to a vector:
vector<function<void()>> myFunctions;
myFunctions.push_back(bind(&foo, 1));
myFunctions.push_back(bind(&bar, 2.0));
myFunctions.push_back(bind(&baz, 1, 2.0));
// Call the functions in a loop:
vector<function<void()>>::iterator it = myFunctions.begin();
while (it != myFunctions.end())
{
(*it)();
it++;
}
return 0;
}
Note that you can do the loop much easier if your compiler supports C++11:
// Call the functions in a loop:
for (const auto& f : myFunctions)
{
f();
}
Boost.Bind also supports passing in certain parameters dynamically instead of binding them to pre-determined values. See the documentation for more details. You could also trivially alter the above code to support return values (if they are of the same type), by replacing void with the return type, and altering the loop to do something with the returned value.
I haven't used the STL much before, but I started to on this huffman compression project. Everything seems to work except the "for_each" function, which wont except a function argument. Since I don't normally use xcode (I usually use eclipse cdt) I'm not sure if the problem is with my code or with xcode.
This is the Huff.h file
class Huff {
private:
typedef pair<char, int> c_pair;
vector<Node> nodes;
vector<Code> code;
string content;
void copy_to(c_pair c);
public:
Huff(string);
~Huff();
string compress();
bool set_content();
string get_content();
string get_compress();
};
And this is the part of the Huff.cpp file that will not work.
//---Compress---
void Huff::copy_to(c_pair c){
Node n(c.second, c.first, NULL, NULL);
nodes.push_back(n);
}
string Huff::compress(){
map<char, int> freq;
for(int i = 0; i < content.length(); i++)
freq[content[i]]++;
for_each(freq.begin(), freq.end(), copy_to); //I've also tried this->copy_to
return "110";
}
for_each(freq.begin(), freq.end(), copy_to); //I've also tried this->copy_to
copy_to is a member function which cannot be passed to std::for_each.
What you need is a callable entity which doesn't need implicit this : such an entity can be either functor or free function, and in C++11, lambda also.
The lambda solution would be pretty simple if you can use it:
for_each(freq.begin(),
freq.end(),
[this](c_pair & c) { this->copy_to(c); } );
Learn about lambda expression here:
What is a lambda expression in C++11?
As pointed out, you can't use a member function that way with for_each.
The C++03 alternative is to use mem_fun and bind1st to build a function object:
std::for_each(freq.begin(), freq.end(),
std::bind1st(std::mem_fun(&Huff::copy_to), this));
Or using Boost.Bind:
std::for_each(freq.begin(), freq.end(),
boost::bind(&Huff::copy_to, this, _1));