-
Notifications
You must be signed in to change notification settings - Fork 340
How to test if a member std::function is empty, and how to reset it to nullptr? #321
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
I think you are on the right track with adding your conversion to bool. I recently (0d4a99a) fixed a bug that allowed conversions to Are you using a new enough build to have this fix in it? |
Yes, I'm using b7e8897 from Dec. 29, 2016. But it doesn't seem to work. Do I have to do something to "force" the cast to a bool? Or in scripting, should I just be able to write I get:
I've tried various variations of type conversions to bool (they compile fine), along the lines of: chai.add(type_conversion<decltype(MyClass::callbackFunc), bool>([](decltype(MyClass::callbackFunc) f) { return f != nullptr; })); |
oh, it might actually be the |
Nope, that doesn't work either. In that case, I get: if (o.callbackFunc) { // gives Error: "Condition not boolean"
print("callback set");
}
if (!o.callbackFunc) { // gives Error: "Error with prefix operator evaluation: '!'" With parameters: (Function)
print("callback not set");
}
o.callbackFunc = 0; // gives Error: "Unable to find appropriate'=' operator." With parameters: (Function, const int) That's when I use the following bindings: chai.add(fun(&MyClass::callbackFunc), "callbackFunc");
chai.add(type_conversion<decltype(MyClass::callbackFunc), bool>([](decltype(MyClass::callbackFunc) f) { return f != nullptr; })); // or return static_cast<bool>(f);
chai.add(fun([](decltype(MyClass::callbackFunc)& fn, int& p) {
if (p==0) {
fn = nullptr;
}
else {
throw(std::runtime_error("Attempt to assign int that's non-zero to a function"));
}
}), "="); My assignment to (for example) 0 doesn't work either... Should I be registering these with my std::function type as the arguments (as I am now), or should I be using Proxy_Function or boxed values or something? (but then I don't know how to get access to my actual function) |
I believe we have a combination of things going on. The first is that I don't see any current tests for directly exposing a Even a simple test of just making a member that is a std::function, then trying to call that fails in an unexpected way. I think this is a consequence of how dynamic objects and their methods are implemented. The second issue seems to be the way function objects are registered and handled internally, so it's not able to find the conversion operator. For the moment you will need to handle it through getters and setters kind of things, and registering of callbacks. Something like:
We'll leave this issue open and I'll see if I can figure out something that can work a bit more naturally. |
Here is an example program (Gist) that illustrates what I'm trying right now, maybe you'll find a way to do what I'm wanting... Thanks! |
Okay, but in response to your last comment, note that I am able to call my callback fine from scripting... |
huh, I was not able to in my tests... interesting. I'll be sure to check what you are doing. |
FYI I was able to call (via scripting) a callback member std::function that had a) been set in C++ (assigning a lambda) or b) set in ChaiScript (assigning a lambda |
(I just updated the Gist to show the success of calling both C++ and ChaiScript-defined callbacks.) |
Just revisiting this (a few years later ;-). I was almost able to get what I wanted by exposing a separate ChaiScript function on my function type, to test whether the
Then, ideally you'd be able to do:
However, this doesn't work either...well, the "empty" test works fine if Any other ideas or tips I could try? Thanks. |
Okay, the following seems to work for me. Unfortunately it captures all Assignable_Proxy_Functions, not just ones with the arguments and return type I want, but that's not a big deal for me. If I had multiple callback types to support, I could handle them all in this single "empty" method (with a different
|
In terms of resetting the function to be empty after it's defined, it would help if the method What do you think about changing this line: ChaiScript/include/chaiscript/dispatchkit/proxy_functions.hpp Lines 707 to 710 in b0c1483
to return a reference to the std::function<Func>& internal_function() const
{
return m_f.get();
} And/or adding a void clear()
{
m_f.get() = std::function<Func>{};
} I'd be happy to submit this as a PR, if you'll accept it. |
That is changing the function signature, so I'm not entirely sure if tests will pass afterwards. But if things are still working, it should be okay. |
I use nullptr to initialize a std::function variable. Not sure it's correct. |
That's correct in C++ (e.g. to reset it; you don't need to initialize a new one), but the issue I was having was in ChaiScript... |
This is a question not addressed in the cheatsheet, as far as I can tell... I asked a question two weeks ago on the forum, but haven't seen any responses there -- sorry for the repeat posting.
I have a C++ class member that holds a callback function pointer. It is a
std::function
, so it's valid for it to be empty (nullptr
). I have no problems binding the class in ChaiScript, but I don't know the proper way to test if that member is empty, nor how to set it tonullptr
(or 0).In scripting, I am able to create an instance of my class, assign a lambda function to it, and evaluate the function (e.g. using
obj.callbackFunc(3.1f)
). But I don't know how to check if it's empty, or how to reset it tonullptr
(or 0). For the empty (boolean) test, I tried adding a type conversion:That doesn't work, I get a "Condition not boolean" when trying to test the member. For the assignment, I tried various permutations of
operator=
(taking an int argument, i.e. 0), but haven't yet hit on something that worked.I can make a specific method to check or reset that member, but I'd rather something that worked "automatically" for any type of
std::function
variable.For the emptiness test, I came across this in the docs:
but that doesn't seem to work (it returns false whether or not my callbackFunc is set to something), presumably because
std::function
is an object and not (directly) a pointer...Any suggestions?
Desired Behaviour
The text was updated successfully, but these errors were encountered: