How to create multiple caller functions by another function - c++

I'm trying to create a function call stack like this, but so that it goes to caller_1_100:
void callee(void) {
// prints out final call stack
}
void caller_1_3(void) { callee(); }
void caller_1_2(void) { caller_1_3(); }
void caller_1_1(void) { caller_1_2(); }
I know I could use a recursive function to do this, but for now I want to try out both ways.
So I was wondering if there was a way to create this sort of caller functions automatically in C++, as I want to make the function call stack to go down at least 100 in depth.
However, from what I searched it doesn't seem possible in C++? Should I use python or some other language to create then change to C++?

You could use a function template with a specialization for your base case. For example:
template <size_t I>
void caller_1()
{
caller_1<I + 1>();
}
template <>
void caller_1<100>()
{
callee();
}
Keep in mind that since templates are resolved at compile time any decent optimizing compiler will almost certainly optimize out the intermediate calls, so you probably won't see them in a stack trace. See this example.

As you said, you want to have at least 100 in depth, it can be 100, 200, or others. This is like having dynamic function definition. It is not a feature of a compiled language. JS or Python can achieve this more easily.
A solution with C++ can be having a class with a id property and a public function which will be called by others. Then instantiate X instances of the class where X is your depth and call the function of the instances as you want.

Related

Pointer to function from another pointer

I'm new to c++ and I'm trying to make a generic switch (i.e. the device, not the C++ statement) that could be used to blink lights, turn beeps on and off, etc, in my Arduino project.
I could create a switchable interface and implement that in the classes that I want to "switch". But since I'm doing it as study purposes and I saw the pointer-to-functions ability in C++ (that is new to me since I come from C# and Java), I tough it would be a good opportunity to give it a try...
The problem is that I can pass the function in my code only if it's a local function but it won't work if I try to pass a function from another object like a led for example.
Some code to illustrate the problem. This is the switch.cpp, it recieves the On and Off functions in it's constructor and it has a update method that is called inside the loop method in the Arduino ino main class:
auto_switch.cpp
using switch_function = void(*)();
auto_switch::auto_switch(const switch_function on_function, const switch_function off_function, const int max_speed_count)
{
//sets all variables...
}
void auto_switch::update(const unsigned long millis)
{
//turn switch on and off...
}
And this is my ino file
ino file
#include <Arduino.h>
#include "led.h"
#include "auto_switch.h"
led* main_led;
auto_switch* led_switch;
int slow_speed;
//ugly code
void turn_led_on()
{
main_led->turn_on();
}
//ugly code
void turn_led_off()
{
main_led->turn_off();
}
void setup() {
main_led = new led(2, 3, 4, true, color::white);
//ugly code
led_switch = new auto_switch(turn_led_on, turn_led_off, 3);
slow_speed = led_switch->add_speed(100, 100, 3, 1000);
led_switch->set_active_speed(slow_speed);
led_switch->turn_on();
}
void loop() {
led_switch->update(millis());
}
It works but I had to make a local function (turn_led_on and turn_led_off) to be able to assign the inner functions as a parameter to the auto_switch constructor, the parts that I've wrote //ugly code
I wanted to do something like this, without the glue code in between:
//doesn't work
led_switch = new auto_switch(main_led->turn_on, main_led->turn_off, 3);
Is it possible? I've read something about static pointer to function and some std functions that help with that, if I get it right the glue code is necessary in this case so that the compiler can know where the functions are coming from I guess (from which object), but since the functions I need to call cannot be static I've discarded this option, and the std functions I believe it can't be used with the Arduino or could but shouldn't for performance limitations...
Anyway, does it make sense, can it be done using pointer to functions or should I create a interface or something different?
Before deciding how to do it, the qquestion is what do you want to do and why. Because, maybe there are better alternatives using simple C++ idioms.
Option 1: specialization with polymorphism
Do you want to specialize some functions of your switch, so instead of calling the function of the auto_switch you'd call dome more specialized ones ?
In this case you wouldn't do:
//doesn't work
led_switch = new auto_switch(main_led->turn_on, main_led->turn_off, 3);
but instead you would rely on polymorphism with virtual functions in the base class:
class auto_switch {
...
virtual void turn_on();
virtual void turn_off();
...
};
and write a specialized class for the leds:
class led_witch : public auto_switch {
...
void turn_on() override;
void turn_off() override;
...
};
In fact, the compiler will generate some function pointers behind the scene, but you don't have to care:
auto_switch s1=new auto_switch(...);
auto_switch s2=new led_switch(...); // no problem !!
s1->turn_on(); // calls auto_switch::turn_on()
s2->turn_on(); // calls led_switch::turn_on() since the real type of s2 is led_switch
But event if each object's behavior is dynamic on the the base of the real class of the object, the objects of the same class share a behavior that was predefined at compile time. If this is not ok, go to the next option.
Option 2: the member function pointer
The functions of another objects can only be invoked with that object at hand. So having a function pointer to a led function is not sufficient: you also need to know on which led it shall be applied.
This is why member function pointers are different and somewhat constraint: you can only invoke functions of class of your member function pointer. If polymorphism is sufficient (i.e. if derived class has a different implementation of a function already foreseen in the base classe) then you are lucky. If you want to use a function that only exists in the derived class and not in the base class, it won't compile.
Here a simplified version of auto_swith: I provide a function, but allso a pointer to the object on which the function has to be invoked:
class auto_switch{
void (led::*action)();
led *ld;
public:
auto_switch(void(led::*a)(), led*l) : action(a), ld(l) {}
void go () { (ld->*action)(); }
};
// usage:
auto_switch s(&led::turn_off, &l1);
s.go();
Online demo
Option 3 : the functional way (may that's what you're looking for ?)
Another variant would be to use the standard functional library to bind a member function and the object on which it shall be executed (as well as any need parameters):
class auto_switch{
std::function<void()> action;
public:
auto_switch(function<void()>a) : action(a) {}
void go () { action(); }
};
Here you can bind anything: any function of any class:
auto_switch s(bind(&led::turn_off, l1));
s.go();
auto_switch s2(bind(&blinking_led::blink, l2));
s2.go();
Online demo
Option 4 : command pattern
Now if you want to perform something on an object when you turn on and off the switch, but you need total flexibility, you can just implement the command pattern : this lets you execute anything on any object. And you don't even need a function pointer.

Trying to pass a function from a class to a variadic template function

So I have a group project that is comparing the sort times of various sorting functions. I am trying to cut down the amount of copy/pasting code by using a variadic template function. I have read everything I can find on google about them and how to pass functions as parameters. It has been literally DAYS of working on this, and I can't seem to make this work. I've been able to pass a function that is defined in my main cpp file outside of a class, but I can't make it work for the functions that belong to a class.
My group has asked me to abandon this idea (we are running out of time), but I feel like I am so close to getting it. If anyone can help out with the syntax, I would be so grateful. I also tried using the function type from the functional library, which was the only way that semi-worked. I did find this question on stack overflow and the guy had the same error I was getting about using '&', but I still can't seem to make this work.
edit
As per the comments, I tried to make the code as basic and concise as possible. :)
I spent more time than I should have trying to find the function that I had gotten to work, but I did not save a copy of it. I read that I should include code that allows others to duplicate the error, but I have not been able to re-create it. The best I can do is a hypothetical example at this point.
Lets say I have a function in a class called Sorts:
void Sorts::InsertionSort(vector<int> &v_small, int length)
{
//does the thing that sorts the stuff
cout << "display the sorted stuff" << endl
}
and a vector in a class called Data:
class Data{
public
vector<int> dataSmall;
};
both of these are in a separate header file. For simplicity, lets call it "header." :)
run_timer(InsertionSort, vector_to_sort, size_of_vector);
I also have a function, in my cpp file, that (is attempting) to take a function parameter, a vector parameter, and a size parameter.
template <class Ret, class... Args> class function<Ret(Args...)>
run_timer3(function<void(Args...)> sort_func(int), vector<int>& array, int size...)
{
//start the timer
//call function to time, sort_func sometimes has 3 parameters though
sort_func(array, size);
//stop the timer
//calculate and write to file
}
I know I should be able to figure this out with generic examples but I'll just be honest it does not compute. All I need is to know how to pass a function that exists in a class. Although now that I lost the function that was working, maybe I need some help making the function definition as well. :(
This was probably the most helpful page I had found on variadic templates.
Sorry if this is to similar to the one I linked before, but I really can't understand what it is I'm doing wrong. I really don't want to have to have the same block of code with different variables 162 times. If anyone can offer guidance I will send you cyber feet-kisses. Thanks!
Since your question contains way more code then I feel like sifting through, I'll just give you an example on how to pass a function to a template.
#include <iostream>
template <typename F>
void foo(F f) {
f();
}
struct bar {
void print() {
std::cout << "bar\n";
}
void baz() {
foo([&]() { print(); });
}
};
void print() {
std::cout << "free\n";
}
int main () {
foo(print);
bar b;
b.baz();
foo([&]() { b.print(); });
}
A free function can simply be passed in. If you want to pass a member-function you can wrap it in a lambda.

alias a template function that has no parameter for more concise calling

How to alias a certain template function to make it called by using shorter syntax?
From ....
getSystem<SystemX>()-> //get semi-singleton instance of "SystemX"
... to something like this:-
getSystem<SystemX>-> or
getSystem(SystemX)-> or
{SystemX}-> or
SystemX=> (can I define new strange operator?)
At first, I don't think it is a problem at all, but after several months, I think there might be a more concise way (syntax) to call it. (I use it in 400+ location).
I believe it is possible by using the same trick as std::is_enable_t<T>=std::is_enable<T>::value. (?)
full code
My poor workarounds
Besides making the name shorter e.g. getSystem<SystemA>()-> to ss<A>()-> , here are my workarounds.
Solution A
Instead of calling getSystem<SystemA>()->, I would call SystemA:: instead.
Disadvantage:
Every function of system now become static function.
There can't be any 2 instance of the same system inside my program anymore.
Common disadvantage of singleton : Global variable, break single responsibility, etc.
Solution B
By using macro, the result is exactly what I want :-
#define S(param) getSystem<param>()
S(SystemA)->fa()
However, macro has some disadvantages.
I feel that this is not a place to use this type of hack.
Sorry, if it is too newbie, I am very new to C++.
How about:
class SystemB : public SystemBase {
inline auto getSystemA(void) { return getSystem<SystemA>(); }
inline auto getSystemB(void) { return getSystem<SystemB>(); }
void fb();
};
void SystemB::fb(){
getSystemA()->fa();
}
Since you want to use the SystemBase::getSystem from the SystemB object, the function goes in the SystemB class.

C++ using callbacks of an arbitrary class with arbitrary parameters

I want to implement a class with a function able to callback to methods from the object that called that function, without information about it.
Imagine we want to callback to some methods of the class Game from Library:
void Game::display(string a) {
cout << a << endl;
}
int Game::sum(int a, int b) {
return a + b;
}
void Game::start() {
lib = new Library();
lib->doSomething(/* somehow pass information about the functions*/);
}
And then:
void Library::doSomething(list_of_callbacks L /*or something like this*/) {
L[0]("hi"); //L[0] is Game::display
L[1](2,3); //L[1] is Game::sum
}
It needs to work not just with Game, but with any class. The methods we want to call back may need access to the object's attributes (so not necessarily static).
I'm kinda new to C++; I've been searching on the topic for hours now but in most cases the return type or the parameters of all the callback methods are the same. I've tried to get something working with templates and std::function / std::bind but unsuccessfully.
Thanks, and sorry if I didn't make myself clear enough, it's my first post around here.
EDIT:
The doSomething function is going to be generated (translated) by an external tool, which has information about the list of functions (like, the function in L[0] takes these parameters or these others, etc).
If what I'm asking can't be done in C++, isn't there any other way to achieve the same goal? Being able to get information from the caller?

Passing function pointer with scope resolution operator arduino

I'm a newbie to arduino and programming.
I've included a library inside my own library in arduino, but first library contains a function which has a pointer function as a parameter. It is an interrupt service routine(ISR) but I need to call a function in my cpp file when interrupt is occurred. So I need to pass the pointer of that function to the first library code. It works well when I use it in .ino file, I can pass it like,
attachInterrupt(functionISR_name);
but when I use it in .cpp file, I get errors. my function is like,
void velocity::functionISR_name(){
//some code
}
but how can I pass the pointer of this function to the first library function? I tried this way but got errors,
attachInterrupt(velocity::functionISR_name);
You cannot pass a method to a function which expects a function, unless you define it static.
write it static :
static void velocity::functionISR_name()
and
attachInterrupt(&velocity::functionISR_name);
Unfortunately the static method is not bound to a specific instance any more. You should use it only together with a singleton. On Arduino you should write the class like shown below in the code snipped:
class velocity
{
static velocity *pThisSingelton;
public:
velocity()
{
pThisSingelton=this;
}
static void functionISR_name()
{
pThisSingelton->CallWhatEverMethodYouNeeded();
// Do whatever needed.
}
// … Your methods
};
velocity *velocity::pThisSingelton;
velocity YourOneAndOnlyInstanceOfThisClass;
void setup()
{
attachInterrupt(&velocity::functionISR_name);
// …other stuff…
}
This looks ugly, but in my opinion it is totally okay with Arduino as the opportunities are very limited on such a system.
Thinking again over it, I would personal go for the approach Sorin mentioned in his answer above. That would be more like that:
class velocity
{
public:
velocity()
{
}
static void functionISR_name()
{
// Do whatever needed.
}
// … Your methods
};
velocity YourOneAndOnlyInstanceOfThisClass;
void functionISR_name_delegation()
{
YourOneAndOnlyInstanceOfThisClass.functionISR_name();
}
void setup()
{
attachInterrupt(functionISR_name_delegation);
// …other stuff…
}
It would also save you some bytes for the pointer you need in the first example.
As a site note: For the future, please post the exact code (for e.g. attachInterrupt needs more parameter) and copy&paste the error messages. Usually error are exact at a place you do not suspect. This question was an exception. Normally I and other would ask for better specification.
You pass a pointer to the function but the function is a class member. Likely the call will be invalid because the this pointer will be garbage(may compile fine but will throw strange errors at runtime).
You need to define a plain vanilla function, outside of any class, and use that.
If you don't have a very complex project you can get away with having a global pointer to the class instance you should use and just delegate the call in your new function.
If you want to do thing the right way you need some mechanism to get the instance pointer I talked about above. Usually this involves either a singleton or some factory pattern.
Example:
class Foo {
void method() {
x = 5;
}
int x;
}
Having a callback on method will crash because you have an invalid pointer for this so x=5 will write 5 somewhere randomly in memory.
What you need is somehting like:
static Foo* foo_instance; // Initialized somewhere else.
void method_delegator() {
foo_instance->method();
}
Now you can pass method_delegator to the function. It will work because you now also pass foo_instance for this pointer.