Help with compile error(C++)

Started by
5 comments, last by SiCrane 12 years, 6 months ago
I am trying to get the following to work( for practice ). Kinda psuedocode-ish

<template T>
class Foo{
//...
template<typename Func1>
void apply(const Func1&){
for each element in current Foo
Func1(*current)
}
void addFoo(const T& val){ ... } //add Node with value val.
Foo(const Foo<T>& f){
_fooSize = f._fooSize;
f.apply( std::mem_fun( &(Foo<T>::addObject)); //Problem arises or starts here I guess.
};


I wanted to use the apply algorithm in f.apply to call the current addObject with all values in f. This is the compile error:

error: no match for call to '(const std::mem_fun1_ref_t<void, List<int>, const int&>) (int&)'
note: candidates are: _Ret std::mem_fun1_ref_t<_Ret, _Tp, _Arg>::operator()(_Tp&, _Arg) const [with _Ret = void, _Tp = List<int>, _Arg = const int&]


I'm not quite sure how to solve this. Any help would be appreciated.
Edge cases will show your design flaws in your code!
Visit my site
Visit my FaceBook
Visit my github
Advertisement
I'm not quite sure I understand what you're trying to do, but it looks like you might be forgetting to give the function a this pointer.
It would be helpful if I could compile your code myself, but without all the code that's not an option.

Here's some code which shows how you can use std::mem_fun, maybe it will help you solve your problem.


template <typename T>
class Foo
{
public:
void foo(T i)
{
//Make sure printf won't break in case T isn't an int.
static_assert(std::is_integral<T>::value, "T must be an integer");

printf("foo(%u)\n", i);
}

template <typename Func>
void runMemberFunction(Func func, T i)
{
//Run function with the this pointer as the first argument.
func(this, i);
}
};

int main(int, const char**)
{
Foo<int> myFoo;
auto fooFunc = std::mem_fun(&Foo<int>::foo);
myFoo.runMemberFunction(fooFunc, 42);

//Run the function with myFoo as the first argument (simulating the this pointer).
fooFunc(&myFoo, 42);

return 0;
}
Why don't you just post the actual code that gives you the error instead of requiring us to guess? Work is hard.

Stephen M. Webb
Professional Free Software Developer

example:

#include <functional>
#include <iostream>
using namespace std;

template<typename T>
class Foo{
private:
struct FooNode{
T val;
FooNode *prev, *next;
FooNode(const T& val = T(), FooNode *p = 0, FooNode *n =0): val(val),prev(p),next(n){};
};
private:
FooNode *_head, *_tail;
public:
Foo(): _head(0),_tail(0){}

//Copy-CTOR
//I want to call the pushBack function, hence creating new object from the given obj's elements
Foo(const Foo<T>& obj){
obj.apply(mem_fun(&Foo<T>::pushBack));
}
void pushBack(const T& val){
if (_head == 0) {
_tail = _head = new FooNode(val);
}else{
FooNode* tmp = _tail;
tmp->next = new FooNode(val,_tail,0);
_tail = tmp;
}
}

template<typename Func1>
void apply(const Func1& op)const{
for (FooNode *curr = _head; curr; curr = curr->next) {
op(curr->val);
}
}
};

template<typename T> void print(const T& arg){ cout << arg << " "; }

int main(){
Foo<int> obj;
obj.pushBack(4);
obj.pushBack(3);
obj.apply(print<int>);

Foo<int> job(obj);

//LET OS DELETE MEMORY, don't want to write it now, note I can't use additional dependencies
return 0;
}
Edge cases will show your design flaws in your code!
Visit my site
Visit my FaceBook
Visit my github
You need to bind the member function to an object instance. One method:

Foo(const Foo<T>& obj){
obj.apply(std::bind(std::mem_fn(&Foo<T>::pushBack), this, std::placeholders::_1));
}

You need to bind the member function to an object instance. One method:

Foo(const Foo<T>& obj){
obj.apply(std::bind(std::mem_fn(&Foo<T>::pushBack), this, std::placeholders::_1));
}



is there anyway I can do this without using the new features?
Edge cases will show your design flaws in your code!
Visit my site
Visit my FaceBook
Visit my github
You could use boost or create your own function object that acts as a closure for the bound member function. Unfortunately, the C++03 standard library feature that would theoretically help with this, std::bind1st, doesn't play nicely with member functions that have reference parameters like your pushBack() member function. If you really do want to use that then you can alter your pushBack() member function to accept its argument by value and use:

obj.apply(bind1st(mem_fun(&Foo<T>::pushBack), this));

Also, you might want to initialize the pointers to null before you call the apply() member function.

This topic is closed to new replies.

Advertisement