"Не слишком специализируйтесь."
"Так что вы не можете просто писать код. Вам нужно что-то сделать с культурой и с тем, как выражать идеи. То есть я ни разу не пожалел о времени, потраченном на историю и математику. Математика обостряет ваш ум, история даёт некоторое представление о ваших ограничениях и о том, что происходит в мире. Так что не будьте слишком уверены. Найдите время, чтобы вести сбалансированную жизнь."
https://habr.com/ru/news/757164/
"Так что вы не можете просто писать код. Вам нужно что-то сделать с культурой и с тем, как выражать идеи. То есть я ни разу не пожалел о времени, потраченном на историю и математику. Математика обостряет ваш ум, история даёт некоторое представление о ваших ограничениях и о том, что происходит в мире. Так что не будьте слишком уверены. Найдите время, чтобы вести сбалансированную жизнь."
https://habr.com/ru/news/757164/
Хабр
Бьёрн Страуструп дал разработчикам несколько ценных советов на всю жизнь
72-летний изобретатель языка программирования C++ Бьёрн Страуструп в интервью платформе Honeypot.io дал всем разработчикам независимо от их многолетнего опыта несколько ценных советов на всю жизнь. В...
👍1
"did everybody expect that to happen?" спрашивает докладчик. Такого уж я точно не ожидала. Он сравнил ускорение (speedup на легенде) двух приложений: wait-free находит сумму через std::atomic, в то время как mutex находит ту же сумму, используя одноименную блокировку и обычные (неатомарные) переменные.
Внезапно оказалось, что wait-free масштабируется значительно хуже простого mutex.
Детали и более подробное устройство атомиков тут: https://www.youtube.com/watch?v=ZQFzMfHIxng
#cpp #multithreading
Внезапно оказалось, что wait-free масштабируется значительно хуже простого mutex.
Детали и более подробное устройство атомиков тут: https://www.youtube.com/watch?v=ZQFzMfHIxng
#cpp #multithreading
Опенсорсная реализация пятой Цивилизации (с "картофельной" графикой). Доступно для Android (включая F-Droid) и для десктопа. Переведена на русский.
https://github.com/yairm210/Unciv
#github #opensorce
https://github.com/yairm210/Unciv
#github #opensorce
Прошла бесплатный быстрый тест (занимает всего 15 минут) на знание английского EF SET. Без регистрации и смс. Ссылка на тест внизу страницы https://www.efset.org/ru/cefr/
#english
#english
Пример простой, но при этом достаточно эффективной реализации многопоточного паттерна event loop. Да на хабре, да на английском. Используется std::function для задач, std::condition_variable.
https://habr.com/ru/articles/665730/
#cpp #multithreading #habr
https://habr.com/ru/articles/665730/
#cpp #multithreading #habr
Хабр
Idiomatic Event Loop in C++
Introduction Event Loop as a Tool TL;DR; Show Me The Code! The Basic Implementation The Power of std::function The Power of std::condition_variable The Power of Double Buffering A Couple of Remarks...
👍1
В std::list метод erase() возвращает итератор, следующий за удаленным элементом.
Почему? Ну во-первых итератор на удаленный элемент не валиден (он ведь удален), а во вторых это позволяет например организовать удаление из списка в цикле, вот так (1):
#cpp
Почему? Ну во-первых итератор на удаленный элемент не валиден (он ведь удален), а во вторых это позволяет например организовать удаление из списка в цикле, вот так (1):
std::list<int> lst = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 };
auto it = lst.begin();
while ( it != lst.end() ) {
if ( *it % 2 ) {
it = lst.erase(it); // (1) верно
//lst.erase(it); ++it; // (2) не верно
//lst.erase(it++); // (3) верно
} else {
++it;
}
}
Вариант (2) упадет (почему?), вариант (3) тоже рабочий, но возможно более сложный для понимания, чем (1) #cpp
std::list, обычно реализуемый как двусвязный список, имеет метод вставки элемента в начало push_front(). Понятно, что для двусвязного списка эта операция константна.
Разработчики же интерфейса std::vector предусмотрительно не стали реализовывать метод push_front(), так как добавление элемента в начало массива влечет необходимость переместить все элементы, а это уже O(n).
Однако вставить элемент в начало вектора все же можно, для этого следует воспользоваться методом insert():
Разработчики же интерфейса std::vector предусмотрительно не стали реализовывать метод push_front(), так как добавление элемента в начало массива влечет необходимость переместить все элементы, а это уже O(n).
Однако вставить элемент в начало вектора все же можно, для этого следует воспользоваться методом insert():
std::vector<int> v;#cpp
for (int i = 0; i < 5; ++i) {
v.insert(v.begin(), i);
}
// v = {4, 3, 2, 1, 0}
🔥1
Добавленный в C++11 std::forward_list реализует односвязный список, в отличие от двухсвязного std::list, и потому занимает меньше памяти. Однако за это приходится своеобразно платить. Допустим, мы находимся на элементе 3 и хотим его удалить. Для этого нужно изменить связь предыдущего элемента 2, но мы не можем к нему вернуться, так как связь идет в одну сторону (в двухсвязном в обе). Поэтому методы добавления и удаления элементов в forward_list изменяют элемент после указанного, так что мы можем обновить ссылку. Для этого в таком списке используется например не метод erase (которого вообще нет), а метод erase_after.
А что же делать с первым элементом, спросите вы, мои котятки? Как его удалить, если erase_after(begin) удалит элемент после первого, то есть второй? Для этого разработчики придумали интересный костыль, а именно метод before_begin(), который возвращает итератор на несуществующий элемент перед первым (аналогично тому, как во всех контейнерах end() указывает на несуществующий элемент после последнего). Вот так вот 😉.
#cpp
А что же делать с первым элементом, спросите вы, мои котятки? Как его удалить, если erase_after(begin) удалит элемент после первого, то есть второй? Для этого разработчики придумали интересный костыль, а именно метод before_begin(), который возвращает итератор на несуществующий элемент перед первым (аналогично тому, как во всех контейнерах end() указывает на несуществующий элемент после последнего). Вот так вот 😉.
#cpp
👍3
Найдите ошибку:
#cpp
std::vector<int> vec = {0,1,2,3,4,5,6,7,8,9};
auto mid = vec.cbegin() + 5;
auto findIt = std::find(vec.cbegin(), mid, 10);
if (findIt == vec.cend()) {
std::cout << "Not found";
} else {
std::cout << "Found";
}
Ошибочно выведется "Found", хотя 10 нет в векторе. Почему? Дело в том, что std::find не возвращает итератор end контейнера, если элемент не найден (указатель на end попросту негде взять). Вернет же функция второй параметр (last), если элемент не обнаружен. Правильно бы было сравнивать в if с mid (который не просматривается, к слову).#cpp
👍2