Scott Meyers - Effective Modern C++

Здесь есть возможность читать онлайн «Scott Meyers - Effective Modern C++» весь текст электронной книги совершенно бесплатно (целиком полную версию без сокращений). В некоторых случаях можно слушать аудио, скачать через торрент в формате fb2 и присутствует краткое содержание. Город: Sebastopol, Год выпуска: 2014, ISBN: 2014, Издательство: O’Reilly, Жанр: Программирование, на английском языке. Описание произведения, (предисловие) а так же отзывы посетителей доступны на портале библиотеки ЛибКат.

Effective Modern C++: краткое содержание, описание и аннотация

Предлагаем к чтению аннотацию, описание, краткое содержание или предисловие (зависит от того, что написал сам автор книги «Effective Modern C++»). Если вы не нашли необходимую информацию о книге — напишите в комментариях, мы постараемся отыскать её.

Coming to grips with C++11 and C++14 is more than a matter of familiarizing yourself with the features they introduce (e.g., auto type declarations, move semantics, lambda expressions, and concurrency support). The challenge is learning to use those features
— so that your software is correct, efficient, maintainable, and portable. That's where this practical book comes in. It describes how to write truly great software using C++11 and C++14 — i.e., using
C++.
Topics include:
■ The pros and cons of braced initialization,
specifications, perfect forwarding, and smart pointer make functions
■ The relationships among
,
, rvalue references, and universal references
■ Techniques for writing clear, correct,
lambda expressions
■ How
differs from
, how each should be used, and how they relate to C++'s concurrency API
■ How best practices in “old” C++ programming (i.e., C++98) require revision for software development in modern C++
Effective Modern C++ For more than 20 years,
'
books (
,
, and
) have set the bar for C++ programming guidance. His clear, engaging explanations of complex technical material have earned him a worldwide following, keeping him in demand as a trainer, consultant, and conference presenter. He has a Ph.D. in Computer Science from Brown University.
“After I learned the C++ basics, I then learned how to use C++ in production code from Meyers' series of Effective C++ books. Effective Modern C++ is the most important how-to book for advice on key guidelines, styles, and idioms to use modern C++ effectively and well. Don't own it yet? Buy this one. Now.”
Herb Sutter
Chair of ISO C++ Standards Committee and C++ Software Architect at Microsoft

Effective Modern C++ — читать онлайн бесплатно полную книгу (весь текст) целиком

Ниже представлен текст книги, разбитый по страницам. Система сохранения места последней прочитанной страницы, позволяет с удобством читать онлайн бесплатно книгу «Effective Modern C++», без необходимости каждый раз заново искать на чём Вы остановились. Поставьте закладку, и сможете в любой момент перейти на страницу, на которой закончили чтение.

Тёмная тема
Сбросить

Интервал:

Закладка:

Сделать

compilers see a mismatch between the type of the argument ( const char[6]) and the type of the parameter taken by push_back(a reference to a std::string). They address the mismatch by generating code to create a temporary std::stringobject from the string literal, and they pass that temporary object to push_back. In other words, they treat the call as if it had been written like this:

vs.push_back( std::string("xyzzy" )); // create temp, std::string

// and pass it to push_back

The code compiles and runs, and everybody goes home happy. Everybody except the performance freaks, that is, because the performance freaks recognize that this code isn't as efficient as it should be.

To create a new element in a container of std::strings, they understand, a std::stringconstructor is going to have to be called, but the code above doesn't make just one constructor call. It makes two. And it calls the std::stringdestructor, too. Here's what happens at runtime in the call to push_back:

1. A temporary std::stringobject is created from the string literal "xyzzy". This object has no name; we'll call it temp . Construction of temp is the first std::stringconstruction. Because it's a temporary object, temp is an rvalue.

2. temp is passed to the rvalue overload for push_back, where it's bound to the rvalue reference parameter x. A copy of xis then constructed in the memory for the std::vector. This construction — the second one — is what actually creates a new object inside the std::vector. (The constructor that's used to copy xinto the std::vectoris the move constructor, because x, being an rvalue reference, gets cast to an rvalue before it's copied. For information about the casting of rvalue reference parameters to rvalues, see Item 25.)

3. Immediately after push_backreturns, temp is destroyed, thus calling the std::stringdestructor.

The performance freaks can't help but notice that if there were a way to take the string literal and pass it directly to the code in step 2 that constructs the std::stringobject inside the std::vector, we could avoid constructing and destroying temp . That would be maximally efficient, and even the performance freaks could contentedly decamp.

Because you're a C++ programmer, there's an above-average chance you're a performance freak. If you're not, you're still probably sympathetic to their point of view. (If you're not at all interested in performance, shouldn't you be in the Python room down the hall?) So I'm pleased to tell you that there is a way to do exactly what is needed for maximal efficiency in the call to push_back. It's to not call push_back. push_backis the wrong function. The function you want is emplace_back.

emplace_backdoes exactly what we desire: it uses whatever arguments are passed to it to construct a std::stringdirectly inside the std::vector. No temporaries are involved:

vs. emplace_back("xyzzy"); // construct std::string inside

// vs directly from "xyzzy"

emplace_backuses perfect forwarding, so, as long as you don't bump into one of perfect forwarding's limitations (see Item 30), you can pass any number of arguments of any combination of types through emplace_back. For example, if you'd like to create a std::stringin vsvia the std::stringconstructor taking a character and a repeat count, this would do it:

vs.emplace_back(50, 'x'); // insert std::string consisting

// of 50 'x' characters

emplace_backis available for every standard container that supports push_back. Similarly, every standard container that supports push_frontsupports emplace_front. And every standard container that supports insert(which is all but std::forward_listand std::array) supports emplace. The associative containers offer emplace_hintto complement their insertfunctions that take a “hint” iterator, and std::forward_listhas emplace_afterto match its insert_after.

What makes it possible for emplacement functions to outperform insertion functions is their more flexible interface. Insertion functions take objects to be inserted , while emplacement functions take constructor arguments for objects to be inserted . This difference permits emplacement functions to avoid the creation and destruction of temporary objects that insertion functions can necessitate.

Because an argument of the type held by the container can be passed to an emplacement function (the argument thus causes the function to perform copy or move construction), emplacement can be used even when an insertion function would require no temporary. In that case, insertion and emplacement do essentially the same thing. For example, given

std::string queenOfDisco("Donna Summer");

both of the following calls are valid, and both have the same net effect on the container:

vs. push_back(queenOfDisco); // copy-construct queenOfDisco

// at end of vs

vs. emplace_back(queenOfDisco); // ditto

Emplacement functions can thus do everything insertion functions can. They sometimes do it more efficiently, and, at least in theory, they should never do it less efficiently. So why not use them all the time?

Because, as the saying goes, in theory, there's no difference between theory and practice, but in practice, there is. With current implementations of the Standard Library, there are situations where, as expected, emplacement outperforms insertion, but, sadly, there are also situations where the insertion functions run faster. Such situations are not easy to characterize, because they depend on the types of arguments being passed, the containers being used, the locations in the containers where insertion or emplacement is requested, the exception safety of the contained types' constructors, and, for containers where duplicate values are prohibited (i.e., std::set, std::map, std::unordered_set, std::unordered_map), whether the value to be added is already in the container. The usual performance-tuning advice thus applies: to determine whether emplacement or insertion runs faster, benchmark them both.

That's not very satisfying, of course, so you'll be pleased to learn that there's a heuristic that can help you identify situations where emplacement functions are most likely to be worthwhile. If all the following are true, emplacement will almost certainly outperform insertion:

The value being added is constructed into the container, not assigned. The example that opened this Item (adding a std::stringwith the value "xyzzy"to a std::vector vs) showed the value being added to the end of vs— to a place where no object yet existed. The new value therefore had to be constructed into the std::vector. If we revise the example such that the new std::stringgoes into a location already occupied by an object, it's a different story. Consider:

Читать дальше
Тёмная тема
Сбросить

Интервал:

Закладка:

Сделать

Похожие книги на «Effective Modern C++»

Представляем Вашему вниманию похожие книги на «Effective Modern C++» списком для выбора. Мы отобрали схожую по названию и смыслу литературу в надежде предоставить читателям больше вариантов отыскать новые, интересные, ещё непрочитанные произведения.


Отзывы о книге «Effective Modern C++»

Обсуждение, отзывы о книге «Effective Modern C++» и просто собственные мнения читателей. Оставьте ваши комментарии, напишите, что Вы думаете о произведении, его смысле или главных героях. Укажите что конкретно понравилось, а что нет, и почему Вы так считаете.

x