Calling C++ member function pointer from a struct - c++

I have found information on calling C++ member function pointers and calling pointers in structs, but I need to call a member function pointer that exists inside of a structure, and I have not been able to get the syntax correct. I have the following snippet inside a method in class MyClass:
void MyClass::run() {
struct {
int (MyClass::*command)(int a, int b);
int id;
} functionMap[] = {
{&MyClass::commandRead, 1},
{&MyClass::commandWrite, 2},
};
(functionMap[0].MyClass::*command)(x, y);
}
int MyClass::commandRead(int a, int b) {
...
}
int MyClass::commandWrite(int a, int b) {
...
}
This gives me:
error: expected unqualified-id before '*' token
error: 'command' was not declared in this scope
(referring to the line '(functionMap[0].MyClass::*command)(x, y);')
Moving those parenthesis around results in syntax errors recommending using .* or ->* neither of which work in this situation. Does anyone know the proper syntax?

Use:
(this->*functionMap[0].command)(x, y);
Tested and compiles ;)

I haven't compiled any code, but just from looking at it I can see you're missing a few things.
Remove the MyClass:: from where you call the function pointer.
Need to pass the this pointer to the functions (if they use any instance data), so that means you need an instance of MyClass to call it.
(After a bit of research) It looks like you need to do something like this (also thanks to #VoidStar):
(this->*(functionMap[0].command)(x, y));

Related

request for member 'find' in 'm', which is of non-class type 'int'

getting error /code/Solution.cpp:8:14: error: request for member 'find' in 'm', which is of non-class type 'int'
if(m.find(s)!=m.end())return;
I also tried to change the location of unordered_map to outside the class ,still getting
the same error.
class Solution {
public:
int maxsum;
unordered_map<string,int>m;
void solve(int m,vector<int>a,int sum,int i){
string s = to_string(sum)+" "+to_string(i);
if(m.find(s)!=m.end())return;
m[s]++;
if(i==a.size())return;
if(sum+a[i]<m){maxsum=max(maxsum,sum+a[i]);
solve(m,a,sum+a[i],i+1);}
solve(m,a,sum,i+1);
}
int backPack(int m, vector<int> &a) {
// write your code here
maxsum=0;
solve(m,a,0,0);
return maxsum;
}
};
You called both the map class variable m, and the first function parameter m. The parameter shadows the class variable, so your compiler sees it instead.
You should try to avoid using the same name for multiple variables that can be seen from the same scope, and while you’re at it you might want to use more meaningful names instead of just using single letters, to make your code more readable.

Calling a C++ pointer method inside a map function [duplicate]

I'm getting a compile error (MS VS 2008) that I just don't understand. After messing with it for many hours, it's all blurry and I feel like there's something very obvious (and very stupid) that I'm missing. Here's the essential code:
typedef int (C::*PFN)(int);
struct MAP_ENTRY
{
int id;
PFN pfn;
};
class C
{
...
int Dispatch(int, int);
MAP_ENTRY *pMap;
...
};
int C::Dispatch(int id, int val)
{
for (MAP_ENTRY *p = pMap; p->id != 0; ++p)
{
if (p->id == id)
return p->pfn(val); // <--- error here
}
return 0;
}
The compiler claims at the arrow that the "term does not evaluate to a function taking 1 argument". Why not? PFN is prototyped as a function taking one argument, and MAP_ENTRY.pfn is a PFN. What am I missing here?
p->pfn is a pointer of pointer-to-member-function type. In order to call a function through such a pointer you need to use either operator ->* or operator .* and supply an object of type C as the left operand. You didn't.
I don't know which object of type C is supposed to be used here - only you know that - but in your example it could be *this. In that case the call might look as follows
(this->*p->pfn)(val)
In order to make it look a bit less convoluted, you can introduce an intermediate variable
PFN pfn = p->pfn;
(this->*pfn)(val);
Try
return (this->*p->pfn)(val);
Just to chime in with my own experience, I've come across an error in g++ caused by this statement:
(this -> *stateHandler)() ;
Where stateHandler is a pointer to a void member function of the class referenced by *this. The problem was caused by the spaces between the arrow operator. The following snippet compiles fine:
(this->*stateHandler)() ;
I'm using g++ (GCC) 4.4.2 20090825 (prerelease). FWIW.
p->pfn is a function pointer. You need to use * to make it function. Change to
(*(p->pfn))(val)

Error with implement map within template c++

I need to use a map with various type within es int,int or char,int or char,char....
This is my c++ code:
#include <iostream>
#include<map>
using namespace std;
template< class A, class B >
class MyClass {
private:
std::map<A,B> DatMap;
public:
MyClass<K,T>(){
DatMap = 0;
}
~MyClass(){
delete DatMap;
}
void DatInsert( A k ,B v ) {
DatMap.insert( std::pair<A,B>( k, v) );
}
};
int main(){
DatMap<int,int> datmap1();
diz1.DatInsert();
}
I found this error on: diz1.DatInsert(); line
the error is:
error: request for member ‘DatInsert’ in ‘datmap1’, which is of non-class type ‘DatMap<int, int>()’|
What am I doing wrong?
This is a function declaration:
// functon datamap1, returns DatMap<int, int>
DatMap<int,int> datmap1();
You need
DatMap<int,int> datmap1;
Alternatively, this syntax is valid since C++11
DatMap<int,int> datmap1{};
Vlad and Jauncho make good points but have both missed another error
DatMap<int,int> datmap1(); isn't valid also because there is no public type DatMap exposed. The class is MyClass
You should be saying:
MyClass<int,int> datmap1; // or datmap1{};
There are several errors in the code.
For example identifiers K and T used in this code snippet
MyClass<K,T>(){
DatMap = 0;
}
are undefined. Also the assignment DataMap by zero is invalid.
You shall not delete DatMap in destructor
~MyClass(){
delete DatMap;
}
because DatMap is not a pointer.
These both statements in main
DatMap<int,int> datmap1();
diz1.DatInsert();
are invalid. The first one is a declaration of a function that shall not be compiled. And the second statement contains call of member function DatInsert without arguments. You defined the function as having two parameters
void DatInsert(A k ,B v){
DatMap.insert(std::pair<A,B>(k,v));
}
so you need to provide two arguments.

Using member functions to deal with objects in the heap (c++)

I'm a beginner with C++, and this is a pretty basic syntax question, but i can't seem to find an answer elsewhere. Any input would be welcome. Here is a simplified version of the problem.
Say I have a class 'pair'
class pair
{
int a;
int b;
public:
pair(int x,int y)
{
a=x;
b=y;
}
int lookup()
{
return this->a+b;
}
};
Then i instanciate and copy that instance to a spot on the heap.
int func()
{
...
pair test(1,2);
pair *ptr=new pair;
*ptr=test;
}
Now here is the key. I don't destroy this memory allocation after the function ends. I want to use it later in this other function. The problem is, i would prefer to keep it in the heap and NOT have to copy it over to the stack(in the actual program it is very large). I would therefore like to do something like this:
int otherfunc()
{
...
int sum=*ptr.lookup;
}
but I get a compiler error. I end up having to do something like:
int otherfunc()
{
...
point temp=*ptr;
int sum=temp.lookup;
}
While this works, it is redundant, and when dealing with really large things it can even potentially cause an overflow. Anyone know the syntax for calling the method using the pointer while keeping it on the heap? Thanks.
I believe this is what you are trying to do:
int sum = ptr->lookup();
And as an aside, this:
return this->a+b;
Would probably be better as just this:
return a+b;
The expression *ptr.lookup will be interpreted as *(ptr.lookup), which is why you get the syntax error because ptr.lookup does not make sense. You'll need to tell the compiler dereference ptr first by using the parenthesis: (*ptr).lookup.
Because pointers are common in C (and C++), the (*a).b can be written in a simpler form: a->b.
Also, lookup is a function even if it does not take any parameters. You need to call it with ():
int sum=ptr->lookup();

Calling the function pointed by a Pointer-to-Member-Function from within a struct

I have a class Test with a peculiar data structure.
A member of class Test is a std::map where the key is a std::string and the mapped value is a struct defined as follows:
typedef struct {
void (Test::*f) (void) const;
} pmf_t;
Initialization of the map is OK. The problem is when I am trying to call the function pointed. I made up a toy example reproducing the problem. Here it is:
#include <iostream>
#include <map>
using namespace std;
class Test;
typedef void (Test::*F) (void) const;
typedef struct {
F f;
} pmf_t;
class Test
{
public:
Test () {
pmf_t pmf = {
&Test::Func
};
m["key"] = pmf;
}
void Func (void) const {
cout << "test" << endl;
}
void CallFunc (void) {
std::map<std::string, pmf_t>::iterator it = m.begin ();
((*it).second.*f) (); // offending line
}
std::map<std::string, pmf_t> m;
};
int main ()
{
Test t;
t.CallFunc ();
return 0;
}
Thanks in advance,
Jir
The name of the pmf_t type is f, so the first change is to remove the * to get second.f. That gives you a pointer-to-member value. To use a pointer-to-member, you need an instance. The only one you have available of the correct type is this, so use it with the ->* operator:
(this->*it->second.f)();
You need parentheses around the whole thing, or else the compiler thinks you're trying to call it->second.f() (which isn't allowed) and then applying the result to ->*.
The offending line is trying to call a member function without any object to call it on. If the intention is to call it for the this object, I believe the call should look like
( this->* ((*it).second.f) )();
Where this->* is the syntax for dereferencing a pointer-to-member for the current object. ((*it).second.f) is the pointer retrieved from the map, and () is the call operator for actually calling the function.
This is perhaps good as an exercise, but otherwise of limited use.
I think you might want to check out the C++ FAQ on this one. The syntax is apparently pretty tricky to get right (they actually recommend using a macro).
It might be too late for this question but, the seemingly complex synatax can be break down to two simple lines so it looks pretty clear:
void CallFunc (void)
{
pmf_t t = m["key"]; //1>get the data from key
(this->*t.f)(); //2>standard procedure to call pointer to member function
}
try this:
(this->*((*it).second.f)) ();