Projection Functions

Combining Multiple Projection Functions in C++

Can I combine multiple projection functions for a single algorithm?

Abstract art representing computer programming

Combining multiple projection functions for a single algorithm in C++ is possible but requires careful design.

While standard algorithms typically accept a single projection function, you can chain projections or compose them to achieve the desired result.

Method 1: Chaining Projections

You can chain projections by having one projection call another. Here's an example where we sort Player objects first by Level and then by Name:

#include <vector>
#include <iostream>
#include <algorithm>

struct Player {
  std::string Name;
  int Level;
};

int main() {
  std::vector<Player> Party {
    {"Legolas", 49},
    {"Gimli", 47},
    {"Gandalf", 49},
    {"Aragorn", 47}
  };

  std::ranges::sort(Party, {}, [](const Player& P) {
    return std::tie(P.Level, P.Name);
  });

  for (const auto& P : Party) {
    std::cout << "[" << P.Level << "] "
      << P.Name << "\n";
  }
}
[47] Aragorn
[47] Gimli
[49] Gandalf
[49] Legolas

In this example, the projection function returns a std::tie of Level and Name, allowing std::ranges::sort() to sort by both criteria.

Method 2: Composition of Projections

You can create higher-order functions that compose multiple projection functions. Here’s an example:

#include <vector>
#include <iostream>
#include <algorithm>
#include <tuple>

struct Player {
  std::string Name;
  int Level;
};

template<typename F1, typename F2>
auto compose(F1 f1, F2 f2) {
  return [f1, f2](const auto& x) {
    return std::make_tuple(f1(x), f2(x));
  };
}

int main() {
  std::vector<Player> Party {
    {"Legolas", 49},
    {"Gimli", 47},
    {"Gandalf", 49},
    {"Aragorn", 47}
  };

  auto projection = compose(
    [](const Player& P) { return P.Level; },
    [](const Player& P) { return P.Name; }
  );

  std::ranges::sort(Party, {}, projection);

  for (const auto& P : Party) {
    std::cout << "[" << P.Level << "] "
      << P.Name << "\n";
  }
}
[47] Aragorn
[47] Gimli
[49] Gandalf
[49] Legolas

Key Points:

  • Chaining Projections: Use std::tie or similar constructs to chain projections within a single function.
  • Composition: Create higher-order functions to compose multiple projections into one.

Combining projections can provide powerful and flexible sorting and transformation capabilities in your algorithms, allowing you to handle complex sorting criteria effectively.

Answers to questions are automatically generated and may not have been reviewed.

Free, Unlimited Access

Professional C++

Comprehensive course covering advanced concepts, and how to use them on large-scale projects.

Screenshot from Warhammer: Total War
Screenshot from Tomb Raider
Screenshot from Jedi: Fallen Order
Contact|Privacy Policy|Terms of Use
Copyright © 2024 - All Rights Reserved