Home > Mobile >  How to efficiently perform a list of transformations in place on an object in C ?
How to efficiently perform a list of transformations in place on an object in C ?

Time:11-08

I'm new to C and am a bit confused by how references, values, and move semantics work. I want to implement a function that can take an event, apply a list of transforms, and output the transformed event.

Here's a code snippet:


std::vector<Event (*)(Event)> transforms = ...;

Event process(Event baseEvent) {
    Event&& e = std::move(baseEvent);
    for(auto fn: this->transforms) {
        e = fn(e);
    }
    return e;
}

The requirements:

  1. The baseEvent should not be modified in place by process. I believe this is achieved here since I am passing the event in by value.
  2. The process method's copy of baseEvent should be modified in place by each transform. I want to be careful not to make any extra copies. Each transform function takes in the event as an rvalue reference. However, I'm not sure if this is being achieved.

I read up on move semantics and tried to reason through the code, but not sure if the requirements are being met.

CodePudding user response:

Your transformation function takes an Event and returns a new Event. It is literally impossible to build a "should modify in place" function on top of that.

So your function is already pretty much as close as you can get to what you want, except for the rvalue reference thing. There's no point in doing that. You want to std::move into the function, so that the argument can be move-constructed, but otherwise just assign back to the one object you already have.

Event process(Event e) {
    for(auto fn: this->transforms) {
        e = fn(std::move(e));
    }
    return e;
}

If you want the transformation functions to actually modify in place, you need to give them the ability to do so:

std::vector<void (*)(Event&)> transforms = ...;

Event process(Event e) {
    for(auto fn: this->transforms) {
        fn(e);
    }
    return e;
}
  • Related