Лайфхаки визуального сторителлинга 😉
Рассказываем, почему это полезно и как его построить, чтобы было понятно всем: и менеджерам, и разработчикам, и дизайнерам⬆
И да, вы справитесь, даже если не умеете рисовать! Александр Зинченко, СТО Яндекс 360, поделился инструментами для быстрых и удобных скетчей. А ещё рассказал про сложности передачи идей в проектных командах, которые можно решить с помощью визуального сторителлинга😎
Больше интересной и полезной информации в канале от команды Яндекс 360
Рассказываем, почему это полезно и как его построить, чтобы было понятно всем: и менеджерам, и разработчикам, и дизайнерам
И да, вы справитесь, даже если не умеете рисовать! Александр Зинченко, СТО Яндекс 360, поделился инструментами для быстрых и удобных скетчей. А ещё рассказал про сложности передачи идей в проектных командах, которые можно решить с помощью визуального сторителлинга
Больше интересной и полезной информации в канале от команды Яндекс 360
Please open Telegram to view this post
VIEW IN TELEGRAM
Please open Telegram to view this post
VIEW IN TELEGRAM
👾 Vita3K — экспериментальный эмулятор PlayStation Vita для Windows, Linux, macOS и Android. Проект уже демонстрирует впечатляющие результаты: часть коммерческих игр и множество homebrew-приложений запускаются, хотя разработчики предупреждают о возможных багах. Среди поддерживаемых игр — Persona 4 Golden, VA-11 HALL-A и другие культовые проекты.
Проект распространяется под лицензией GPLv2 и активно развивается благодаря поддержке сообщества. Важно отметить, что эмулятор не предназначен для пиратства — игры должны быть дампами с оригинальных носителей.
🤖 GitHub
@cpluspluc
Проект распространяется под лицензией GPLv2 и активно развивается благодаря поддержке сообщества. Важно отметить, что эмулятор не предназначен для пиратства — игры должны быть дампами с оригинальных носителей.
🤖 GitHub
@cpluspluc
🔧 OpenXRay — движок STALKER с открытым исходным кодом получает вторую жизнь.
Сообщество энтузиастов серии STALKER продолжает развивать OpenXRay — улучшенную версию оригинального движка X-Ray Engine. Проект не просто исправляет баги и добавляет 64-битную поддержку, но и открывает новые возможности для модификации игр.
Хотя разработчики подчеркивают стремление сохранить ванильный геймплей, проект уже включает оптимизации рендеринга, поддержку геймпадов и новые инструменты для модмейкеров.
🤖 GitHub
@cpluspluc
Сообщество энтузиастов серии STALKER продолжает развивать OpenXRay — улучшенную версию оригинального движка X-Ray Engine. Проект не просто исправляет баги и добавляет 64-битную поддержку, но и открывает новые возможности для модификации игр.
Хотя разработчики подчеркивают стремление сохранить ванильный геймплей, проект уже включает оптимизации рендеринга, поддержку геймпадов и новые инструменты для модмейкеров.
🤖 GitHub
@cpluspluc
🎯 ▪ Задача: "Числа-близнецы с кастомным компаратором" (C++ для продвинутых)
У вас есть массив
1.
2.
3. Если таких пар несколько, вернуть все, отсортированные по A, затем по B
▪ Ограничения:
-
-
▪ Пример:
Вход:
Вывод:
✅ Минимальная разница = 1
🧠 Уловки задачи:
Наивное сравнение O(N²) слишком медленно
Нужно использовать сортировку + два указателя или бинарный поиск
✍️ Решение:
Идея решения — сначала разделить все числа на четные и нечетные, отсортировать их, а затем с помощью двух указателей найти пары с минимальной разницей. После этого собрать все такие пары и отсортировать результат по условию.
▪ Код:
```cpp
#include <iostream>
#include <vector>
#include <algorithm>
#include <cmath>
using namespace std;
int main() {
int N;
cin >> N;
vector<int> even, odd;
for (int i = 0; i < N; ++i) {
int x;
cin >> x;
if (x % 2 == 0) even.push_back(x);
else odd.push_back(x);
}
sort(even.begin(), even.end());
sort(odd.begin(), odd.end());
vector<pair<int, int>> result;
int min_diff = INT_MAX;
int i = 0, j = 0;
while (i < even.size() && j < odd.size()) {
int a = even[i];
int b = odd[j];
int diff = abs(a - b);
if (diff < min_diff) {
min_diff = diff;
result.clear();
result.emplace_back(a, b);
} else if (diff == min_diff) {
result.emplace_back(a, b);
}
if (a < b) i++;
else j++;
}
sort(result.begin(), result.end());
for (auto& p : result) {
cout << "(" << p.first << "," << p.second << ")\n";
}
return 0;
}```
▪ 🔍 Пошаговый разбор:
✅ Считываем входные данные
✅ Разделяем числа на четные и нечетные
✅ Сортируем оба массива
✅ Используем два указателя, чтобы найти минимальную разницу за O(N)
✅ Если нашли пару с меньшей разницей — сбрасываем результат и добавляем её
✅ Если нашли пару с такой же разницей — просто добавляем
✅ Финально сортируем все найденные пары по A, затем по B
✨ Почему задача хитрая: ✅ Нужно оптимальное решение вместо лобового перебора
✅ Включает тонкую работу с индексами
✅ Требует правильно обрабатывать несколько минимальных пар
✅ Объединяет знания сортировки, двух указателей и поиска пар
💪 Challenge для профи: 👉 Попробуйте реализовать эту задачу с помощью multiset + lower_bound / upper_bound, чтобы избежать сортировки массивов и упростить логику поиска ближайших чисел.
У вас есть массив
N
целых чисел. Нужно найти все пары чисел (A, B), таких что:1.
|A - B|
минимально среди всех пар в массиве2.
A
— четное, а B
— нечетное3. Если таких пар несколько, вернуть все, отсортированные по A, затем по B
▪ Ограничения:
-
1 <= N <= 10^5
-
-10^9 <= A[i] <= 10^9
▪ Пример:
Вход:
arr = [4, 7, 9, 2, 8, 3]
Вывод:
(2,3)
(4,3)
(4,7)
(8,7)
(8,9)
✅ Минимальная разница = 1
🧠 Уловки задачи:
Наивное сравнение O(N²) слишком медленно
Нужно использовать сортировку + два указателя или бинарный поиск
✍️ Решение:
Идея решения — сначала разделить все числа на четные и нечетные, отсортировать их, а затем с помощью двух указателей найти пары с минимальной разницей. После этого собрать все такие пары и отсортировать результат по условию.
▪ Код:
```cpp
using namespace std;
int main() {
int N;
cin >> N;
vector<int> even, odd;
for (int i = 0; i < N; ++i) {
int x;
cin >> x;
if (x % 2 == 0) even.push_back(x);
else odd.push_back(x);
}
sort(even.begin(), even.end());
sort(odd.begin(), odd.end());
vector<pair<int, int>> result;
int min_diff = INT_MAX;
int i = 0, j = 0;
while (i < even.size() && j < odd.size()) {
int a = even[i];
int b = odd[j];
int diff = abs(a - b);
if (diff < min_diff) {
min_diff = diff;
result.clear();
result.emplace_back(a, b);
} else if (diff == min_diff) {
result.emplace_back(a, b);
}
if (a < b) i++;
else j++;
}
sort(result.begin(), result.end());
for (auto& p : result) {
cout << "(" << p.first << "," << p.second << ")\n";
}
return 0;
}```
▪ 🔍 Пошаговый разбор:
✅ Считываем входные данные
✅ Разделяем числа на четные и нечетные
✅ Сортируем оба массива
✅ Используем два указателя, чтобы найти минимальную разницу за O(N)
✅ Если нашли пару с меньшей разницей — сбрасываем результат и добавляем её
✅ Если нашли пару с такой же разницей — просто добавляем
✅ Финально сортируем все найденные пары по A, затем по B
✨ Почему задача хитрая: ✅ Нужно оптимальное решение вместо лобового перебора
✅ Включает тонкую работу с индексами
✅ Требует правильно обрабатывать несколько минимальных пар
✅ Объединяет знания сортировки, двух указателей и поиска пар
💪 Challenge для профи: 👉 Попробуйте реализовать эту задачу с помощью multiset + lower_bound / upper_bound, чтобы избежать сортировки массивов и упростить логику поиска ближайших чисел.
@cpluspluc
Please open Telegram to view this post
VIEW IN TELEGRAM
🦾 Задача с подвохом: Виртуальные функции и конструкторы
Условие:
Что выведет следующий код и почему?
❓ Вопрос:
Что будет выведено? Почему результат может удивить даже опытных C++ разработчиков?
🔍 Разбор:
1️⃣ Мы создаём объект.
Это вызывает конструктор , но сначала выполняется конструктор `Base` (по правилам иерархии).
2️⃣ В конструкторе есть вызов .
Может показаться, что поскольку объект на самом деле , вызовется .
Но! Вот главный подвох:
➡️ В C++, когда вы вызываете виртуальную функцию из конструктора (или деструктора), она не виртуальна для объекта, который ещё не полностью сконструирован.
На момент вызова объект всё ещё только Base, потому что ещё не инициализирован.
✅ Пошаговое выполнение:
- Вызов конструктора :
```
Base constructor
```
- Вызов внутри конструктора :
Это вызовет Base::foo(), а не :
```
Base foo
```
- После завершения конструктора , вызывается конструктор :
```
Derived constructor
```
✅ Итоговый вывод:
```
Base constructor
Base foo
Derived constructor
```
💥 Подвох:
• Многие ожидают, что виртуальные функции работают «магически» всегда.
• Но при вызове из конструктора (или деструктора) виртуальные функции не полиморфны, потому что объект ещё не «стал» Derived полностью.
🛡️ Что нужно помнить:
Никогда не полагайтесь на вызовы виртуальных функций в конструкторах/деструкторах для вызова методов производных классов. Это источник трудноуловимых багов.
✅ Вывод:
C++ строго следует правилам объектной модели: пока объект конструируется (или разрушается), он считается экземпляром того класса, конструктор которого выполняется в данный момент. Это поведение важно помнить при проектировании иерархий классов!
@cpluspluc
Условие:
Что выведет следующий код и почему?
#include <iostream>
class Base {
public:
Base() {
std::cout << "Base constructor\n";
foo();
}
virtual void foo() {
std::cout << "Base foo\n";
}
};
class Derived : public Base {
public:
Derived() {
std::cout << "Derived constructor\n";
}
void foo() override {
std::cout << "Derived foo\n";
}
};
int main() {
Derived d;
return 0;
}
❓ Вопрос:
Что будет выведено? Почему результат может удивить даже опытных C++ разработчиков?
🔍 Разбор:
1️⃣ Мы создаём объект
Derived d;
Это вызывает конструктор
Derived
2️⃣ В конструкторе
Base
foo();
Может показаться, что поскольку объект на самом деле
Derived
Derived::foo()
Но! Вот главный подвох:
➡️ В C++, когда вы вызываете виртуальную функцию из конструктора (или деструктора), она не виртуальна для объекта, который ещё не полностью сконструирован.
На момент вызова
foo()
Derived
✅ Пошаговое выполнение:
- Вызов конструктора
Base
```
Base constructor
```
- Вызов
foo()
Base
Это вызовет Base::foo(), а не
Derived::foo()
```
Base foo
```
- После завершения конструктора
Base
Derived
```
Derived constructor
```
✅ Итоговый вывод:
```
Base constructor
Base foo
Derived constructor
```
💥 Подвох:
• Многие ожидают, что виртуальные функции работают «магически» всегда.
• Но при вызове из конструктора (или деструктора) виртуальные функции не полиморфны, потому что объект ещё не «стал» Derived полностью.
🛡️ Что нужно помнить:
Никогда не полагайтесь на вызовы виртуальных функций в конструкторах/деструкторах для вызова методов производных классов. Это источник трудноуловимых багов.
✅ Вывод:
C++ строго следует правилам объектной модели: пока объект конструируется (или разрушается), он считается экземпляром того класса, конструктор которого выполняется в данный момент. Это поведение важно помнить при проектировании иерархий классов!
@cpluspluc
💥 CLion теперь бесплатен для некоммерческих проектов! 😮
CLion — мощная IDE для разработки на C и C++, стала доступна бесплатно для:
• студентов и всех, кто изучает программирование
• разработчиков open source-проектов
• создателей обучающего и технического контента
Отличная возможность работать в профессиональной среде без затрат 💻
👉 Официальная шпаргалка по горячим клавишам для CLion: https://resources.jetbrains.com/storage/products/clion/docs/CLion_reference_card_all.pdf
@cpluspluc
CLion — мощная IDE для разработки на C и C++, стала доступна бесплатно для:
• студентов и всех, кто изучает программирование
• разработчиков open source-проектов
• создателей обучающего и технического контента
Отличная возможность работать в профессиональной среде без затрат 💻
👉 Официальная шпаргалка по горячим клавишам для CLion: https://resources.jetbrains.com/storage/products/clion/docs/CLion_reference_card_all.pdf
@cpluspluc
🍊 JUCE — фреймворк для создания аудиоприложений на C++. Этот инструмент — must-have для разработчиков аудиоплагинов и музыкальных приложений. Проект предоставляет готовые компоненты для работы с аудио, MIDI и GUI, которые работают на всех платформах, от macOS до Android.
Фреймворк также имеет интеграцию с CMake: можно собрать проект одной командой, а встроенный генератор создаст настройки для Xcode, Visual Studio и Android Studio. Под капотом поддержка современных стандартов вроде C++17 и ARM-архитектур.
🤖 GitHub
@cpluspluc
Фреймворк также имеет интеграцию с CMake: можно собрать проект одной командой, а встроенный генератор создаст настройки для Xcode, Visual Studio и Android Studio. Под капотом поддержка современных стандартов вроде C++17 и ARM-архитектур.
🤖 GitHub
@cpluspluc
🎮 UEVR — универсальный мод для погружения игр Unreal Engine в VR. С помощью UEVR можно превратить практически любой проект на Unreal Engine 4-5 в полноценный VR-эксперимент с поддержкой 6DOF, стереоскопическим 3D и даже эмуляцией motion-контроллеров.
Важно заметить, что разработчики вместо кропотливой адаптации каждой игры работают напрямую с движком. Это открывает путь к исследованию сотен проектов от инди-хорроров до AAA-хитов через шлем VR.
🤖 GitHub
@cpluspluc
Важно заметить, что разработчики вместо кропотливой адаптации каждой игры работают напрямую с движком. Это открывает путь к исследованию сотен проектов от инди-хорроров до AAA-хитов через шлем VR.
🤖 GitHub
@cpluspluc
📚 Librum — читалка с облачной библиотекой и 70 000+ бесплатных книг
С этим инструментом ваша библиотека станет по-настоящему мобильной — проект имеет синхронизацию между устройствами, теги, коллекции и даже статистика чтения — всё под рукой, будь то Windows, Linux или macOS.
Проект полностью открытый, а его команда живёт на донаты. При этом здесь уже есть поддержка редких форматов вроде CBZ (для комиксов) и TIFF, а в дорожной карте — TTS и AI-инструменты для заметок.
🤖 GitHub
@cpluspluc
С этим инструментом ваша библиотека станет по-настоящему мобильной — проект имеет синхронизацию между устройствами, теги, коллекции и даже статистика чтения — всё под рукой, будь то Windows, Linux или macOS.
Проект полностью открытый, а его команда живёт на донаты. При этом здесь уже есть поддержка редких форматов вроде CBZ (для комиксов) и TIFF, а в дорожной карте — TTS и AI-инструменты для заметок.
🤖 GitHub
@cpluspluc
Backend Talks от Яндекс 360
Смотрите записи докладов с митапа от Яндекс 360 для бэкенд-разработчиков, архитекторов и DevOps-инженеров.
На пути к 9999: Игорь Обручев, руководитель группы SRE, рассказал, какими принципами команда руководствуется при создании сервисов, как без паники чинят инциденты и как в этом помогают учения.
Эволюция проектирования общих решений в Яндекс 360: Евгений Ширанков, руководитель команды платформенных сервисов, рассказал про подходы и лайфхаки, которые помогли выдержать рост команды и оставаться в контексте создания общих решений, не переизобретая велосипеды.
Ценности и культура команды: Роман Акинфеев, руководитель бэкенд-разработки, рассказал, почему культура и ценности являются важнейшими активами команды, которые сложно создать и поддерживать, но легко потерять в период взрывного роста.
Больше материалов о технологиях в Яндекс 360
@yandex360team
Смотрите записи докладов с митапа от Яндекс 360 для бэкенд-разработчиков, архитекторов и DevOps-инженеров.
На пути к 9999: Игорь Обручев, руководитель группы SRE, рассказал, какими принципами команда руководствуется при создании сервисов, как без паники чинят инциденты и как в этом помогают учения.
Эволюция проектирования общих решений в Яндекс 360: Евгений Ширанков, руководитель команды платформенных сервисов, рассказал про подходы и лайфхаки, которые помогли выдержать рост команды и оставаться в контексте создания общих решений, не переизобретая велосипеды.
Ценности и культура команды: Роман Акинфеев, руководитель бэкенд-разработки, рассказал, почему культура и ценности являются важнейшими активами команды, которые сложно создать и поддерживать, но легко потерять в период взрывного роста.
Больше материалов о технологиях в Яндекс 360
@yandex360team
⚡️ Kubernetes устраняет проблему безопасности с приватными образами, которую не решали более 10 лет
Ранее, при использовании политики imagePullPolicy: IfNotPresent, kubelet мог запускать контейнеры из приватных образов, даже если pod не передавал нужные imagePullSecrets. Это означало, что уже загруженные образы могли использоваться без повторной проверки прав доступа.
Начиная с Kubernetes v1.33, kubelet теперь проверяет учетные данные pod-а даже для локально кэшированных образов. Если образ найден на узле, kubelet удостоверяется, что pod имеет соответствующие pull credentials, прежде чем разрешить его запуск.
Ожидается, что в v1.34 эта функция перейдёт в бета-стадию и получит дополнительные улучшения.
https://kubernetes.io/blog/2025/05/12/kubernetes-v1-33-ensure-secret-pulled-images-alpha/
Ранее, при использовании политики imagePullPolicy: IfNotPresent, kubelet мог запускать контейнеры из приватных образов, даже если pod не передавал нужные imagePullSecrets. Это означало, что уже загруженные образы могли использоваться без повторной проверки прав доступа.
Начиная с Kubernetes v1.33, kubelet теперь проверяет учетные данные pod-а даже для локально кэшированных образов. Если образ найден на узле, kubelet удостоверяется, что pod имеет соответствующие pull credentials, прежде чем разрешить его запуск.
Ожидается, что в v1.34 эта функция перейдёт в бета-стадию и получит дополнительные улучшения.
https://kubernetes.io/blog/2025/05/12/kubernetes-v1-33-ensure-secret-pulled-images-alpha/
🧵 Пишем свой сетевой стек с нуля: Ethernet и ARP на C
Хочешь разобраться, как работает TCP/IP на самом низком уровне?
В этой статье показано, как реализовать Ethernet и ARP в пользовательском пространстве Linux — на чистом C.
🔌 Что используется:
- TAP-устройство для приёма и отправки "сырых" Ethernet-кадров
- Структуры с
- Чтение и парсинг ARP-пакетов вручную
📦 Что реализуется:
- Создание ARP-запросов и обработка ответов
- Простейший ARP-кэш
- Парсинг и генерация Ethernet-фреймов
- Весь ввод-вывод — в user space
🧠 Зачем это нужно?
- Понимание, как работают сетевые интерфейсы на уровне байтов
- Практика системного программирования на C
- Основа для написания своего сетевого стека: IPv4, ICMP, UDP, TCP
📚 Статья:
https://www.saminiir.com/lets-code-tcp-ip-stack-1-ethernet-arp/
💻 Исходники на GitHub:
https://github.com/saminiir/level-ip
#Linux #Networking #C #TCPIP #ARP #Ethernet #DevLowLevel #СистемноеПрограммирование
Хочешь разобраться, как работает TCP/IP на самом низком уровне?
В этой статье показано, как реализовать Ethernet и ARP в пользовательском пространстве Linux — на чистом C.
🔌 Что используется:
- TAP-устройство для приёма и отправки "сырых" Ethernet-кадров
- Структуры с
__attribute__((packed))
для точного соответствия форматам- Чтение и парсинг ARP-пакетов вручную
📦 Что реализуется:
- Создание ARP-запросов и обработка ответов
- Простейший ARP-кэш
- Парсинг и генерация Ethernet-фреймов
- Весь ввод-вывод — в user space
🧠 Зачем это нужно?
- Понимание, как работают сетевые интерфейсы на уровне байтов
- Практика системного программирования на C
- Основа для написания своего сетевого стека: IPv4, ICMP, UDP, TCP
📚 Статья:
https://www.saminiir.com/lets-code-tcp-ip-stack-1-ethernet-arp/
💻 Исходники на GitHub:
https://github.com/saminiir/level-ip
#Linux #Networking #C #TCPIP #ARP #Ethernet #DevLowLevel #СистемноеПрограммирование
🧪 Jank — диалект Clojure, который вместо JVM использует LLVM и предлагает бесшовную интероперабельность с C++. Разработчики обещают сохранить всю прелесть Clojure: иммутабельные структуры данных, функциональный подход и REPL, но с перспективой нативной производительности.
Пока проект находится в активной разработке, но уже поддерживает базовый синтаксис Clojure и часть core-функций. Для фанатов Clojure, которые мечтают избавиться от JVM-оверхедов, jank может стать интересной альтернативой.
🤖 GitHub
@cpluspluc
Пока проект находится в активной разработке, но уже поддерживает базовый синтаксис Clojure и часть core-функций. Для фанатов Clojure, которые мечтают избавиться от JVM-оверхедов, jank может стать интересной альтернативой.
🤖 GitHub
@cpluspluc
🧠 Задача с подвохом для продвинутых C++ разработчиков
🔹 Уровень: Advanced
🔹 Темы:
📌 Условие
Рассмотрим следующий код:
❓ Вопросы
1. Что будет выведено на экран?
2. Почему
3. Что изменится, если заменить
🔍 Разбор
✅ Ожидаемый вывод:
🔧 Почему так происходит
-
-
- Временный объект уничтожается (вызывается `Dtor`).
-
🔄 Если заменить `reserve(3)` на `resize(3)`
-
-
- Это может привести к копированию или перемещению уже созданных элементов.
⚠️ Подвох
Многие ошибочно считают, что
🧠 Вывод
-
-
- Не путай эти методы — от этого зависит и производительность, и семантика.
📌 Совет:
Если не хочешь лишнего перемещения, используй
@cpluspluc
🔹 Уровень: Advanced
🔹 Темы:
std::vector
, управление памятью, конструкторы/деструкторы, reserve()
vs resize()
📌 Условие
Рассмотрим следующий код:
#include <iostream>
#include <vector>
struct Foo {
Foo() { std::cout << "Ctor\n"; }
~Foo() { std::cout << "Dtor\n"; }
Foo(const Foo&) { std::cout << "Copy\n"; }
Foo(Foo&&) noexcept { std::cout << "Move\n"; }
};
int main() {
std::vector<Foo> v;
v.reserve(3); // Резервируем место под 3 элемента
std::cout << "--- Pushing ---\n";
for (int i = 0; i < 3; ++i) {
v.push_back(Foo());
}
std::cout << "--- Done ---\n";
}
❓ Вопросы
1. Что будет выведено на экран?
2. Почему
reserve()
не предотвращает конструкторы копирования/перемещения? 3. Что изменится, если заменить
reserve(3)
на resize(3)
?🔍 Разбор
✅ Ожидаемый вывод:
--- Pushing ---
Ctor
Move
Dtor
Ctor
Move
Dtor
Ctor
Move
Dtor
--- Done ---
Dtor
Dtor
Dtor
🔧 Почему так происходит
-
Foo()
создаёт временный объект. -
push_back()
вызывает перемещающий конструктор Move
. - Временный объект уничтожается (вызывается `Dtor`).
-
reserve(3)
выделяет память, но не создаёт объектов.🔄 Если заменить `reserve(3)` на `resize(3)`
-
resize(3)
создаст 3 объекта Foo через конструктор по умолчанию. -
push_back(Foo())
добавит четвёртый, возможно вызовет realocation. - Это может привести к копированию или перемещению уже созданных элементов.
⚠️ Подвох
Многие ошибочно считают, что
reserve(n)
создаёт n
объектов. Но это не так — reserve()
только выделяет память, не вызывая конструкторы. Именно поэтому внутри push_back
всё равно происходит перемещение или копирование.🧠 Вывод
-
reserve()
— экономия на реаллокациях, без создания объектов. -
resize()
— создаёт n
объектов, вызывает конструкторы. - Не путай эти методы — от этого зависит и производительность, и семантика.
// Резервирует память, не создаёт объекты
v.reserve(10);
// Создаёт 10 объектов Foo
v.resize(10);
📌 Совет:
Если не хочешь лишнего перемещения, используй
emplace_back()
:
v.emplace_back(); // Вызывает конструктор Foo напрямую внутри вектора
@cpluspluc