I have a class FooBar that contains a member of type Foo. This type can be inherited from so that FooBar has variable behaviour. Foo contains multiple overloads for the accessor method bar.
class FooBar;
class Foo{
friend class FooBar;
virtual void bar(int barIn){ bar_ = barIn; }
virtual void bar(int barIn, float barScale){ bar(int(barIn * barScale)); }
virtual void bar(const Foo& barSource){ bar(barSource.bar_); }
int bar(){ return bar_; }
int bar_;
};
class FooBar{
public:
void bar(int barIn){ foo_.bar(barIn); }
void bar(int barIn, float barScale){ foo_.bar(barIn, barScale); }
void bar(const Foo& barSource){ foo_.bar(barSource); }
int bar(){ return foo_.bar(); }
private:
Foo& foo_;
};
Looks ok so far, but I feel like all the definitions for the FooBar.bar accessor are kind of unnecessary. I know that the compiler inlines them, so there should be no overhead, but the methods all got the same name and are all overloads of each other.
Is there a way in C++ to "export" (I haven't found a better word) the accessor so calls to FooBar.bar are just redirected to FooBar.foo_.bar?
One idea I had was overriding the operator -> for FooBar, but the real case has multiple classes like Foo, so that would only work for one of them.
You could write a real generic forwarder:
class FooBar
{
public:
template<typename... Args>
auto bar(Args&&... args) -> decltype(foo_.bar(std::forward<Args>(args)...))
{
return foo_.bar(std::forward<Args>(args)...);
}
private:
Foo& foo_;
};
(this requires C++11, with C++14 you could even leave out the ->decltype... part)
Related
I have a templated class on some object T. T defines two member functions bar and foo
template<class T>
class A {
public:
void f() {
t_.bar();
t_.foo();
}
private:
T t_;
};
Now I would like be able to tell A (ideally at compile time), to call either foo or bar, but not both. So the idea is to tell A at construction time which member function of T to call.
The solution I have currently in place is to pass a callable void callMember(const T& t) { return t.foo(); } in A's constructor to at runtime call the right member, but I'm wondering if there is a better solution?
You can add a bool template parameter to A that tells it which member function of T to call, and then use a constexpr if on that parameter in the body of f:
template<class T, bool Choice>
class A {
public:
void f() {
if constexpr(Choice) // doesn't strictly have to be constexpr
// if T defines both bar and foo
t_.bar();
else
t_.foo();
}
private:
T t_;
};
Now for some type like:
struct S {
void bar() { std::cout << "bar"; }
void foo() { std::cout << "foo"; }
};
you can do:
A<S, true> a;
a.f(); // calls S::bar
A<S, false> b;
b.f(); // calls S::foo
Here's a demo.
I assume its Ok to have instantiations of A be of different type depending on which method is called. If that is the case I suggest to choose between two types rather than two methods.
Say X is the type with the two methods, then you can do this:
struct X {
void foo() {}
void bar() {}
};
struct Xfoo {
X x;
void foobar() { x.foo(); }
};
struct Xbar {
X x;
void foobar() { x.bar(); }
};
Now the template is:
template<class T>
class A {
public:
void f() {
t_.foobar();
}
private:
T t_;
};
And you either instantiate A<Xfoo> or A<Xbar> rather than A<X>.
I suppose you have more than just one type X, then Xfoo and Xbar can be parametrized on the type to be wrapped.
Say I have a class implementing these two methods :
void foo(const int a);
void foo(const int & a);
How do I resolve ambiguous call like :
int bar = 42;
foo(bar);
EDIT
Both methods are virtual pure inherited from two different parents, doing different things. I would like to have the ability to choose one at call.
Bigger code example :
class B{
virtual void foo(const int a) = 0;
};
class C{
virtual void foo(const int & a) = 0;
};
class A : public B, public C{
void foo(const int a){
// do something
}
void foo(const int & a){
// do something else
}
};
int main(){
A a;
int bar = 42;
a.foo(bar);
}
B and C class are not write by me in my real case, but I have to use these.
The usual solution to this kind of problem is to use a pair of intermediate classes to rename those functions.
struct intermediate1 : base1 {
virtual void f(int x) = 0;
void foo(int x} { f(x); }
};
struct intermediate2 : base2 {
virtual void g(const int& x) = 0;
void foo(const int& x} { g(x); }
};
Now your class can be derived from the two intermediate classes instead of the two original base classes, and your code can override f(whatever) and g(whatever) and call them, rather than the conflicting foo versions.
If you like decorating functions you could mark both of those versions of foo as final.
The c++11 way is to use rvalue ref for the 1st overload:
void foo(int&& rvalue);
void foo(int& lvalue);
read more on rvalue ref at:
https://en.cppreference.com/w/cpp/language/reference
For the multiple-inheritance issue:
struct D:C{
virtual void foo(int&&, std::nullptr_t)=0;
private:
void foo(int v) final { return foo(std::move(v),nullptr); };
};
struct A:B,D{
void foo(int&&, std::nullptr_t=nullptr) override;
void foo(int& ) override;
};
Suppose there are two classes Foo and Bar, with Bar depending on some state provided by Foo. These classes may have a structure as follows:
class Foo
{
public:
// Constructors and destructors
const State& get_state() const;
/* Invalidates and recreates the 'State' object passed by 'get_state' */
void handle_event();
private:
// private member variables
};
class Bar
{
public:
Bar(const Foo& foo);
private:
const State& m_state; //Assigned via foo.get_state()
};
Assuming that besides combining both Foo and Bar into a single class, this the way the State must be passed. Furthermore assume that there can be multiple Bar classes using the State from Foo.
When the handle_event member function is called what is the pattern or "standard" way of handling the situation such that Bar is always in a valid state?
I can imagine that something like Bar registering itself with Foo during its construction can provide such a mechanism. An example of this is below. The issue with this is I feel it may be too tightly coupled.
class Foo
{
public:
void register_dependency(Bar* bar);
void deregister_dependency(Bar* bar);
private:
std::set<Bar *> m_dependencies;
};
class Bar
{
public:
void invalidate_state(const Foo& foo);
};
I would go with a system like the one you have proposed. It is a version of the well-established observer pattern.
If you think other types besides Bar might need state from Foo, then you could use an interface to decouple.
class Foo;
class IFooStateObserver {
public:
virtual ~IFooStateObserver() {}
virtual void invalidate_state(const Foo& foo) = 0;
};
class Foo {
public:
void register_dependency(IFooStateObserver* observer);
void deregister_dependency(IFooStateObserver* observer);
private:
std::set<IFooStateObserver*> m_dependencies;
};
class Bar : public IFooStateObserver {
public:
void invalidate_state(const Foo& foo) override;
};
A similar system could isolate Foo from Bar if necessary.
I have a class MyClass declaration in a header file interface.h and some static functions (foo and bar and a few more) in file1.cpp. The static functions are only used inside file1.cpp but they need to modify private/protected members of MyClass`.
// in "interface.h"
class MyClass {
// maybe declare as friend?
// friend static void foo(MyClass &ref);
private:
double someval;
}
// in "file1.cpp"
static void foo(MyClass &ref) {
ref.someval = 41.0;
}
static void bar(MyClass &ref) {
ref.someval = 0.42;
}
// function that uses foo/bar
void doSomething(MyClass &ref) {
foo(ref);
}
Idea 1: Somehow declare them as friends of MyClass?
Why its not good: They are static AND are in a different compilation unit. Besides that would expose them to the user of MyClass who does not need to know anything about them.
Idea 2: Don't have idea 2.
Sort of linked: Is it possible to declare a friend function as static?
Sort of linked: Is it possible to declare a friend function as static?
Personally I find the whole friend thing a bit of a hack that breaks encapsulation but you've asked a valid question and the answer is that you can achieve what you want with a helper class:
file1.h
class MyClass {
private:
double someval;
friend class MyClassHelper;
};
file1.cpp
#include "file1.h"
struct MyClassHelper {
static void mutateMyClass(MyClass& ref) {
ref.someval=42;
}
};
// in "file1.cpp"
static void foo(MyClass &ref) {
MyClassHelper::mutateMyClass(ref);
}
Are you really sure you want to do it like this? Are you sure you don't want to encapsulate MyClass's mutators inside MyClass itself?
As weird as it may sound (and look), you can actually read & write private members of a class / struct.
It's not pretty, and certainly not encouraged, but doable.
template<typename T>
struct invisible
{
static typename T::type value;
};
template<typename T>
typename T::type invisible<T>::value;
template<typename T, typename T::type P>
class construct_invisible
{
construct_invisible(){ invisible<T>::value = P; }
static const construct_invisible instance;
};
template<typename T, typename T::type P>
const construct_invisible<T, P> construct_invisible<T, P>::instance;
struct MyClass_someval{ typedef double MyClass::*type; };
template class construct_invisible<MyClass_someval, &MyClass::someval>;
static void foo(MyClass &ref) {
ref.*invisible<MyClass_someval>::value = 41.0;
}
When I first saw it I also thought: HOLY S***!
// in "interface.h"
class MyClass {
// maybe declare as friend?
// friend static void foo(MyClass &ref);
public:
friend class SetSomevalClass; // make the classes friends
private:
double someval;
};
class SetSomevalClass // functor class(or function class)
{
public:
double operator()(MyClass n, double data) // this could have been void
{
n.someval = data; //set somevalue to data
return n.someval; //return somevalue
// return is solely used to show result in foo() and bar()
}
};
// in "file1.cpp"
static void foo(MyClass &ref)
{
SetSomevalClass s; //create functor object
//s(ref, 40);
//this would be the end of the foo function(uncommented) if we did not want to show the result
std::cout << "foo()" << s(ref, 40) << std::endl;
//simply to show result
}
static void bar(MyClass &ref)
{
SetSomevalClass s;
//s(ref,2);
//this would be the end of the foo function(uncommented) if we did not want to show the result
std::cout << "bar()" << s(ref, 2) << std::endl;
}
// function that uses foo/bar
void doSomething(MyClass &ref) //calls both foo() and bar()
{
foo(ref);
bar(ref);
}
int main()
{
MyClass s;
doSomething(s);
}// end main
I have a set of classes that are replies from the network. Some classes uses function foo, while others use bar. I was thinking of just have a class that sets the variable inside foo and bar. Then inherit those classes which just only have function foo and bar functions without constantly defining the functions in those classes. For example.
class Foo {
public:
Foo():
foo_(std::string()) {}
virtual ~Foo(){}
const std::string& foo() const { return foo_; }
private:
std::string foo_;
};
class FooReply:
public Foo {
public:
FooReply(){}
explicit FooReply(const std::string& reply):
setFoo(reply) {
}
FooReply(const FooReply& other):
Foo(other) {
}
~FooReply(){}
FooReply& operator=(const FooReply& other) {
Foo::operator=(other);
return *this;
}
};
Would it be better to do this, or should I just make them an interface and just reimplement the foo() function? Since I'm only inheriting one function.