Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

problem with c++ union as argument:

32 views
Skip to first unread message

aotto1968

unread,
Nov 13, 2022, 3:56:58 AM11/13/22
to
Hi, the following code failed to compile on Create

error: no matching function for call to 'ccmqmsgque::MqMsgqueCallbackC::MqMsgqueCallbackC(const
ccmqmsgque::MqMsgqueCallbackC::MqMsgqueCallbackU&)'

namespace ccmqmsgque {
struct MqMsgqueCallbackC {
enum MqMsgqueCallbackE {
PC_CallbackF,
PC_StaticCallbackF,
PC_IService,
PC_IEvent,
PC_IServerSetup,
PC_IServerCleanup,
PC_IBgError
} type;

union MqMsgqueCallbackU {
MqContextC::CallbackF Callback;
MqContextC::StaticCallbackF StaticCallback;
IService * Service;
IEvent * Event;
IServerSetup * ServerSetup;
IServerCleanup * ServerCleanup;
IBgError * BgError;
} call;

public:
MqMsgqueCallbackC(MqContextC::CallbackF const callback);
MqMsgqueCallbackC(MqContextC::StaticCallbackF const callback);
MqMsgqueCallbackC(IService * const service);

MqMsgqueCallbackC(IEvent * const event);
MqMsgqueCallbackC(IServerSetup * const serverSetup);
MqMsgqueCallbackC(IServerCleanup * const serverCleanup);
MqMsgqueCallbackC(IBgError * const bgError);

MqMsgqueCallbackC(MQ_CTX const context, MqMsgqueCallbackC* const copy);

static MK_CBP Create(const union MqMsgqueCallbackU& callback) {
return (MK_CBP) new MqMsgqueCallbackC(callback);
}

static enum MkErrorE Call ( MQ_CALLBACK_SERVICE_CALL_ARGS );
static void Free ( MQ_RT_ARGS MQ_CTX const context, MK_PTR *dataP);
static void Copy ( MQ_RT_ARGS MQ_CTX const context, MK_PTR *dataP);
};
};


Problem

1. I have a union with all possible argument-types and a CTOR for each type
2. Now I want to have a static "Create" function to call the CTOR for each type
3. I know I could write !! 7 !! "Create", just one for every type BUT I want to
use the union

Question, how I do it?


mfg
AO

Bonita Montero

unread,
Nov 13, 2022, 5:05:27 AM11/13/22
to
I'v not completely checked your code, but I guess you need a variant<>.

Marcel Mueller

unread,
Nov 13, 2022, 6:48:17 AM11/13/22
to
Am 13.11.22 um 09:56 schrieb aotto1968:
> Problem
>
> 1. I have a union with all possible argument-types and a CTOR for each type

It seems that you are looking for boost::variant.

> 2. Now I want to have a static "Create" function to call the CTOR for
> each type
> 3. I know I could write !! 7 !! "Create", just one for every type BUT I
> want to
>    use the union

If you want a static Create function that takes your union instead of
the different types you should just invoke the copy constructor. Of
course you have to define one for the union.

Another option is to use a template argument type for Create. Then the
compiler creates the functions for you.

However, I see no use for the static Create over using operator new
directly at all.


Marcel

Michael S

unread,
Nov 13, 2022, 7:28:12 AM11/13/22
to
Compiler errors aside, your code does not make sense.

You probably want something like:

static MK_CBP Create(const union MqMsgqueCallbackU& callback, int createType) {
switch (createType) {
case PC_CallbackF:
return (MK_CBP) new MqMsgqueCallbackC(callback.Callback);
case PC_StaticCallbackF:
return (MK_CBP) new MqMsgqueCallbackC(callback.StaticCallback);
case PC_IService:
return (MK_CBP) new MqMsgqueCallbackC(callback.Service);
etc...
}
}

Michael S

unread,
Nov 13, 2022, 7:44:30 AM11/13/22
to
That's correct.
But it would be better yet if class has just one trivial constructor
with no arguments plus several functions InitializeXXX() with similar
but non-identical names that do actual initialization.
Static polymorphism considered harmful and should be avoided as much
as possible. And static polymorphism through overloaded constructors
is one of the worst forms of static polymorphism, very confusing for
people that try to follow the code years or months later.

>
> Marcel

Bonita Montero

unread,
Nov 13, 2022, 1:52:36 PM11/13/22
to
Am 13.11.2022 um 12:48 schrieb Marcel Mueller:
> Am 13.11.22 um 09:56 schrieb aotto1968:
>> Problem
>>
>> 1. I have a union with all possible argument-types and a CTOR for each
>> type
>
> It seems that you are looking for boost::variant.

Why boost ? C++17 has also variant<>.

Andrey Tarasevich

unread,
Nov 13, 2022, 2:39:23 PM11/13/22
to
On 11/13/2022 12:56 AM, aotto1968 wrote:
>
> error: no matching function for call to
> 'ccmqmsgque::MqMsgqueCallbackC::MqMsgqueCallbackC(const
> ccmqmsgque::MqMsgqueCallbackC::MqMsgqueCallbackU&)'
>

So? You don't have a conversion from `MqMsgqueCallbackU` to
`MqMsgqueCallbackC`. Naturally, the code does not compile.

And how do you expect this conversion to work, if you supply
`MqMsgqueCallbackU` only? The supplied `callback` goes into your `call`
field. But what about `type` field? You can't determine `type` by
`MqMsgqueCallbackU` alone. It is not possible to determine which member
of an union is currently "active".

--
Best regards,
Andrey



Juha Nieminen

unread,
Nov 16, 2022, 4:36:34 AM11/16/22
to
aotto1968 <aott...@t-online.de> wrote:
> error: no matching function for call to 'ccmqmsgque::MqMsgqueCallbackC::MqMsgqueCallbackC(const
> ccmqmsgque::MqMsgqueCallbackC::MqMsgqueCallbackU&)'

On a side note, when asking such questions, it's polite to do some work to
prepare your question rather than just dumping raw code as-is and expecting
people to do that work for you.

The "work" I'm talking about is making the code you are posting as easy for
the reader to understand as possible. This means creating a *minimal*
*complete* piece of code that clearly and succinctly depicts the problem
you are having and asking about. The easier you make for others to read
and understand your code and your question, the more likely it is that
you'll get a good answer. Remove all unnecessary stuff, write a minimal
example that contains only the parts relevant to your question. If necessary,
name your variables and functions more clearly (you can't expect people to
know what some gibberish like "ccmqmsgque" means). Just dumping your existing
code here as-is, with complete disregard to readability and understandability
shows a degree of laziness and unwillingness to help others help you.

As a side benefit, in many cases when you are minimizing your code
you'll sometimes actually find the problem yourself.

Jorgen Grahn

unread,
Nov 19, 2022, 5:43:02 PM11/19/22
to
On Sun, 2022-11-13, aotto1968 wrote:
> Hi, the following code failed to compile on Create
>
> error: no matching function for call to 'ccmqmsgque::MqMsgqueCallbackC::MqMsgqueCallbackC(const
> ccmqmsgque::MqMsgqueCallbackC::MqMsgqueCallbackU&)'
>
> namespace ccmqmsgque {
> struct MqMsgqueCallbackC {
> enum MqMsgqueCallbackE {
> PC_CallbackF,

Unrelated to your question, but:

The idea with namespaces is to group names so you don't need common
prefixes. Your namespace is ccmqmsgque, so you have already
established that the context is "cc", "mq" and "msgque" (whatever
those mean). Your struct can then be called CallbackC. The struct is
also a namespace, so your enum can just be called E. Or you can come
up with a meaningful name, now that it's more obvious that the current
name is poor.

/Jorgen

--
// Jorgen Grahn <grahn@ Oo o. . .
\X/ snipabacken.se> O o .
0 new messages