🍕 Проекции на поля структур

🍕 Проекции на поля структур

В прошлый раз разобрались, что такое проекция и зачем она нужна
. Теперь — самый частый сценарий на практике: структура с кучей полей, и алгоритмы хочется гонять по разным из них, не плодя лямбды.

struct Person {
std::string name;
int age;
double height;
};

std::vector<Person> people = {
{"Алиса", 30, 165},
{"Борис", 25, 180},
{"Виктор", 35, 175},
};

🤠 Одна структура — много ключей

Вся прелесть в том, что один и тот же контейнер крутим по любому полю — меняем только &Person::поле:

// по возрасту
std::ranges::sort(people, std::less{}, &Person::age);
// Борис(25), Алиса(30), Виктор(35)

// самый высокий
auto tallest = std::ranges::max_element(people, std::less{}, &Person::height);
std::cout << tallest->name; // Борис

// найти по имени
auto found = std::ranges::find(people, "Алиса", &Person::name);
std::cout << found->age; // 30

Указатель &Person::age годится в проекции, потому что алгоритм зовёт её через std::invoke, а тот превращает его в p.age. Проекцией может быть что угодно вызываемое.

Заметьте: max_element и find вернули итератор на целого Person. Проекция выбирает ключ, но на выходе всегда исходный элемент.

‼️ sort сортирует на месте. Гоняете сниппеты подряд по одному people — каждый следующий видит уже переставленный вектор (max_element/find это не волнует).


👑 Компаратор + проекция = направление + ключ

Проекция говорит «по какому полю», компаратор — «в каком порядке»:

// по убыванию роста
std::ranges::sort(people, std::greater{}, &Person::height);
// Борис(180), Виктор(175), Алиса(165)

std::less → std::greater — перевернули порядок, поле не трогали.
Компаратор можно сократить до {}, но не выбросить совсем:

std::ranges::sort(people, {}, &Person::age); // ок
std::ranges::sort(people, &Person::age); // не компилируется

Проекция — третий аргумент, поэтому без компаратора &Person::age уедет в его слот. {} этот слот занимает и подставляет дефолт — а дефолт тут std::ranges::less, не std::less (на наших данных без разницы).
Просмотры: 148
Открыть в MAX Сообщить о неточности

Репосты публикации

Публикация канала

Сообщить о неточности

Опишите, что нужно исправить. Если есть источник, добавьте ссылку.

Вы покидаете datool.ru

Ссылка ведёт на внешний сайт. datool.ru не отвечает за его содержимое — проверьте адрес, прежде чем вводить пароли или платёжные данные.

Переход через 10 с

Перейти