Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]
Groups > comp.lang.c++ > #80317 > unrolled thread
| Started by | SIMON <invalid@invalid.invalid> |
|---|---|
| First post | 2021-06-11 17:55 +0000 |
| Last post | 2021-07-06 21:59 -0700 |
| Articles | 14 — 9 participants |
Back to article view | Back to comp.lang.c++
[ #include <stack> ] What's the difference? SIMON <invalid@invalid.invalid> - 2021-06-11 17:55 +0000
Re: [ #include <stack> ] What's the difference? SIMON <invalid@invalid.invalid> - 2021-06-11 18:08 +0000
Re: [ #include <stack> ] What's the difference? scott@slp53.sl.home (Scott Lurndal) - 2021-06-11 18:21 +0000
Re: [ #include <stack> ] What's the difference? Richard Damon <Richard@Damon-Family.org> - 2021-06-11 14:29 -0400
Re: [ #include <stack> ] What's the difference? Kli-Kla-Klawitter <kliklaklawitter69@gmail.com> - 2021-06-11 20:35 +0200
Re: [ #include <stack> ] What's the difference? Manfred <noname@add.invalid> - 2021-06-12 20:06 +0200
Re: [ #include <stack> ] What's the difference? Kli-Kla-Klawitter <kliklaklawitter69@gmail.com> - 2021-06-12 20:12 +0200
Re: [ #include <stack> ] What's the difference? MrSpook_mlauoyv4F_@o18rpnvgrx0dq.co.uk - 2021-06-13 08:34 +0000
Re: [ #include <stack> ] What's the difference? Öö Tiib <ootiib@hot.ee> - 2021-06-13 04:31 -0700
Re: [ #include <stack> ] What's the difference? Andrey Tarasevich <andreytarasevich@hotmail.com> - 2021-06-23 10:17 -0700
Re: [ #include <stack> ] What's the difference? James Kuyper <jameskuyper@alumni.caltech.edu> - 2021-06-24 17:23 -0400
Re: [ #include <stack> ] What's the difference? Andrey Tarasevich <andreytarasevich@hotmail.com> - 2021-07-06 12:50 -0700
Re: [ #include <stack> ] What's the difference? James Kuyper <jameskuyper@alumni.caltech.edu> - 2021-07-06 21:17 -0400
Re: [ #include <stack> ] What's the difference? Andrey Tarasevich <andreytarasevich@hotmail.com> - 2021-07-06 21:59 -0700
| From | SIMON <invalid@invalid.invalid> |
|---|---|
| Date | 2021-06-11 17:55 +0000 |
| Subject | [ #include <stack> ] What's the difference? |
| Message-ID | <sa0877$3h9$1@dont-email.me> |
Does anybody know the significant difference between: > myStack.push(30); > > myStack.emplace(30); > It does the same thing as far as I can see but surely there must be something that I don't know about these two methods.
[toc] | [next] | [standalone]
| From | SIMON <invalid@invalid.invalid> |
|---|---|
| Date | 2021-06-11 18:08 +0000 |
| Message-ID | <sa08tm$9rd$1@dont-email.me> |
| In reply to | #80317 |
On 11/06/2021 18:55, SIMON wrote: > Does anybody know the significant difference between: > >> myStack.push(30); >> >> myStack.emplace(30); >> > It does the same thing as far as I can see but surely there must be > something that I don't know about these two methods. > > These two links says the same thing in different words, of course: <https://www.alphacodingskills.com/cpp/notes/cpp-stack-push.php> <https://www.alphacodingskills.com/cpp/notes/cpp-stack-emplace.php>
[toc] | [prev] | [next] | [standalone]
| From | scott@slp53.sl.home (Scott Lurndal) |
|---|---|
| Date | 2021-06-11 18:21 +0000 |
| Message-ID | <mQNwI.176715$qy1.84680@fx26.iad> |
| In reply to | #80318 |
SIMON <invalid@invalid.invalid> writes: >On 11/06/2021 18:55, SIMON wrote: >> Does anybody know the significant difference between: >> >>> myStack.push(30); >>> >>> myStack.emplace(30); >>> >> It does the same thing as far as I can see but surely there must be >> something that I don't know about these two methods. >> >> > >These two links says the same thing in different words, of course: > ><https://www.alphacodingskills.com/cpp/notes/cpp-stack-push.php> ><https://www.alphacodingskills.com/cpp/notes/cpp-stack-emplace.php> Try a better reference. https://en.cppreference.com/w/cpp/container/stack/push https://en.cppreference.com/w/cpp/container/stack/emplace
[toc] | [prev] | [next] | [standalone]
| From | Richard Damon <Richard@Damon-Family.org> |
|---|---|
| Date | 2021-06-11 14:29 -0400 |
| Message-ID | <PXNwI.318597$N_4.175536@fx36.iad> |
| In reply to | #80317 |
On 6/11/21 1:55 PM, SIMON wrote: > Does anybody know the significant difference between: > >> myStack.push(30); >> >> myStack.emplace(30); >> > It does the same thing as far as I can see but surely there must be > something that I don't know about these two methods. > > > It depends on the type that the stack is made from. push() takes an object of that type, and copies it to the stack. emplace() takes the arguments needed to construct an object of that type an makes a new object from the arguments given. For a type like int, there isn't a difference. If it was a stack of so Point, with a contructor that two arguments it would. to push you would do something like: myStack.push(Point(x, y)); or Point point(x,y); myStack.push(point); while emplace would be myStack.emplace(x,y);
[toc] | [prev] | [next] | [standalone]
| From | Kli-Kla-Klawitter <kliklaklawitter69@gmail.com> |
|---|---|
| Date | 2021-06-11 20:35 +0200 |
| Message-ID | <sa0adp$n2o$1@gioia.aioe.org> |
| In reply to | #80317 |
push and emplace are the same for stack - always!
[toc] | [prev] | [next] | [standalone]
| From | Manfred <noname@add.invalid> |
|---|---|
| Date | 2021-06-12 20:06 +0200 |
| Message-ID | <sa2t3t$1oqb$1@gioia.aioe.org> |
| In reply to | #80317 |
On 6/11/2021 7:55 PM, SIMON wrote: > Does anybody know the significant difference between: > >> myStack.push(30); >> >> myStack.emplace(30); >> > It does the same thing as far as I can see but surely there must be > something that I don't know about these two methods. > > > push() takes a reference to an object that has already been constructed, and pushes it on the stack. This operation involves a copy or move operation. emplace() constructs the object on the stack in-place, using the arguments supplied. This can save a copy or move operation. For 'int' there is no difference. Scott gave you a good reference for the details.
[toc] | [prev] | [next] | [standalone]
| From | Kli-Kla-Klawitter <kliklaklawitter69@gmail.com> |
|---|---|
| Date | 2021-06-12 20:12 +0200 |
| Message-ID | <sa2tek$1tn4$1@gioia.aioe.org> |
| In reply to | #80356 |
> For 'int' there is no difference. The external storage of an int could be moved.
[toc] | [prev] | [next] | [standalone]
| From | MrSpook_mlauoyv4F_@o18rpnvgrx0dq.co.uk |
|---|---|
| Date | 2021-06-13 08:34 +0000 |
| Message-ID | <sa4fu3$48j$1@gioia.aioe.org> |
| In reply to | #80356 |
On Sat, 12 Jun 2021 20:06:53 +0200 Manfred <noname@add.invalid> wrote: >On 6/11/2021 7:55 PM, SIMON wrote: >> Does anybody know the significant difference between: >> >>> myStack.push(30); >>> >>> myStack.emplace(30); >>> >> It does the same thing as far as I can see but surely there must be >> something that I don't know about these two methods. >> >> >> > >push() takes a reference to an object that has already been constructed, One would hope that a modern compiler would optimise out the temporary however so there shouldn't actually be any difference between emplace() and push() in practice.
[toc] | [prev] | [next] | [standalone]
| From | Öö Tiib <ootiib@hot.ee> |
|---|---|
| Date | 2021-06-13 04:31 -0700 |
| Message-ID | <5aa15a6b-44ea-4fa3-9379-3326e6d8c54fn@googlegroups.com> |
| In reply to | #80368 |
On Sunday, 13 June 2021 at 11:34:28 UTC+3, MrSpook_m...@o18rpnvgrx0dq.co.uk wrote:
> On Sat, 12 Jun 2021 20:06:53 +0200
> Manfred <non...@add.invalid> wrote:
> >On 6/11/2021 7:55 PM, SIMON wrote:
> >> Does anybody know the significant difference between:
> >>
> >>> myStack.push(30);
> >>>
> >>> myStack.emplace(30);
> >>>
> >> It does the same thing as far as I can see but surely there must be
> >> something that I don't know about these two methods.
> >>
> >>
> >>
> >
> >push() takes a reference to an object that has already been constructed,
> One would hope that a modern compiler would optimise out the temporary however
> so there shouldn't actually be any difference between emplace() and push()
> in practice.
Take something bit less trivial than int (that is more common in practice):
struct WordCount {std::string word; size_t count;};
I do not think there is any compiler that compiles equal code to emplace("blah", 1)
and push(WordCount{"blah", 1}). Also I do not think there is way how conforming
compiler can do it even in theory.
By my understanding of standard the
* When copy (or move) constructors and destructors do not have side effects
(like it is with int) then those can be elided by as-if rule.
* Copy (or move) elision is allowed during initialization of object with temporary.
* It is mandatory since C++17 when temporary is used as return value (RVO).
* It is allowed when automatic, named, non-volatile, non-function-parameter,
non-catch-clause-parameter is used as return value (NRVO).
* Rest of cases allowed are about constexpr, throws, catches and coroutines.
Did I miss some? WordCount allocates and throws in constructor and is function
parameter of push() so as-if rule does not work nor none of other cases when
copy can be elided.
[toc] | [prev] | [next] | [standalone]
| From | Andrey Tarasevich <andreytarasevich@hotmail.com> |
|---|---|
| Date | 2021-06-23 10:17 -0700 |
| Message-ID | <savqan$4de$1@dont-email.me> |
| In reply to | #80317 |
On 6/11/2021 10:55 AM, SIMON wrote: > Does anybody know the significant difference between: > >> myStack.push(30); >> >> myStack.emplace(30); >> > It does the same thing as far as I can see but surely there must be > something that I don't know about these two methods. Without the exact type of 'myStack' the question is meaningless and does not have an answer. -- Best regards, Andrey Tarasevich
[toc] | [prev] | [next] | [standalone]
| From | James Kuyper <jameskuyper@alumni.caltech.edu> |
|---|---|
| Date | 2021-06-24 17:23 -0400 |
| Message-ID | <sb2t4f$a4d$1@dont-email.me> |
| In reply to | #80554 |
On 6/23/21 1:17 PM, Andrey Tarasevich wrote:
> On 6/11/2021 10:55 AM, SIMON wrote:
>> Does anybody know the significant difference between:
>>
>>> myStack.push(30);
>>>
>>> myStack.emplace(30);
>>>
>> It does the same thing as far as I can see but surely there must be
>> something that I don't know about these two methods.
>
> Without the exact type of 'myStack' the question is meaningless and does
> not have an answer.
What more do you need to know about the the type of myStack that you
don't already know?
The subject line says "#include <stack>", so you can reasonably presume
from its name that myStack is of type std::stack<T, Container> for some
values of T and Container. The differences between push() and emplace()
for that class template are specified precisely in the standard in 22.6.6.1:
template<class T, class Container = deque<T>>
class stack {
public:
using value_type = typename Container::value_type;
private:
Container c;
...
void push(const value_type& x)
{ c.push_back(x); }
void push(value_type&& x)
{ c.push_back(std::move(x)); }
template<class... Args>
decltype(auto) emplace(Args&&... args)
{ return c.emplace_back(std::forward<Args>(args)...); }
[toc] | [prev] | [next] | [standalone]
| From | Andrey Tarasevich <andreytarasevich@hotmail.com> |
|---|---|
| Date | 2021-07-06 12:50 -0700 |
| Message-ID | <sc2c64$ut5$1@dont-email.me> |
| In reply to | #80558 |
On 6/24/2021 2:23 PM, James Kuyper wrote: > On 6/23/21 1:17 PM, Andrey Tarasevich wrote: >> On 6/11/2021 10:55 AM, SIMON wrote: >>> Does anybody know the significant difference between: >>> >>>> myStack.push(30); >>>> >>>> myStack.emplace(30); >>>> >>> It does the same thing as far as I can see but surely there must be >>> something that I don't know about these two methods. >> >> Without the exact type of 'myStack' the question is meaningless and does >> not have an answer. > > What more do you need to know about the the type of myStack that you > don't already know? > The subject line says "#include <stack>", so you can reasonably presume > from its name that myStack is of type std::stack<T, Container> for some > values of T and Container. I need to know what `T` is. I need to know whether `myStack` holds `int`s, or `myStack` holds something else, perhaps some non-trivial, unrelated, possibly "heavy" type, which just happens to be implicitly convertible from `int`. For `T == int` the difference between the variants would be purely conceptual, without any practical consequences. For a "heavy" `T` the difference between these two variants can be substantial. `push` would construct a temporary followed by two moves from it into a new container entry, while `emplace` would construct a new container entry in-place from the twice-forwarded `30`. -- Best regards, Andrey Tarasevich
[toc] | [prev] | [next] | [standalone]
| From | James Kuyper <jameskuyper@alumni.caltech.edu> |
|---|---|
| Date | 2021-07-06 21:17 -0400 |
| Message-ID | <sc2vbg$gr4$1@dont-email.me> |
| In reply to | #80680 |
On 7/6/21 3:50 PM, Andrey Tarasevich wrote: > On 6/24/2021 2:23 PM, James Kuyper wrote: >> On 6/23/21 1:17 PM, Andrey Tarasevich wrote: >>> On 6/11/2021 10:55 AM, SIMON wrote: >>>> Does anybody know the significant difference between: >>>> >>>>> myStack.push(30); >>>>> >>>>> myStack.emplace(30); >>>>> >>>> It does the same thing as far as I can see but surely there must be >>>> something that I don't know about these two methods. >>> >>> Without the exact type of 'myStack' the question is meaningless and does >>> not have an answer. >> >> What more do you need to know about the the type of myStack that you >> don't already know? >> The subject line says "#include <stack>", so you can reasonably presume >> from its name that myStack is of type std::stack<T, Container> for some >> values of T and Container. > > I need to know what `T` is. I need to know whether `myStack` holds > `int`s, or `myStack` holds something else, perhaps some non-trivial, > unrelated, possibly "heavy" type, which just happens to be implicitly > convertible from `int`. > > For `T == int` the difference between the variants would be purely > conceptual, without any practical consequences. > > For a "heavy" `T` the difference between these two variants can be > substantial. `push` would construct a temporary followed by two moves > from it into a new container entry, while `emplace` would construct a > new container entry in-place from the twice-forwarded `30`. That doesn't make the question "meaningless", nor does it prevent the question from having an answer. The question can be answered in full by quoting what the standard says about std::stack<T, Container>::push() and emplace(). The ways in which the behavior depends upon T and Containter are completely determined by what the standard says about those functions, directly or indirectly. The "significant difference" between those two functions that the OP was talking about consists entirely of the differences between what the standard says about them, along with the T-dependent implications of those differences.
[toc] | [prev] | [next] | [standalone]
| From | Andrey Tarasevich <andreytarasevich@hotmail.com> |
|---|---|
| Date | 2021-07-06 21:59 -0700 |
| Message-ID | <sc3cas$g0o$1@dont-email.me> |
| In reply to | #80682 |
On 7/6/2021 6:17 PM, James Kuyper wrote: > On 7/6/21 3:50 PM, Andrey Tarasevich wrote: >> On 6/24/2021 2:23 PM, James Kuyper wrote: >>> ... >>> What more do you need to know about the the type of myStack that you >>> don't already know? >>> The subject line says "#include <stack>", so you can reasonably presume >>> from its name that myStack is of type std::stack<T, Container> for some >>> values of T and Container. >> >> I need to know what `T` is. I need to know whether `myStack` holds >> `int`s, or `myStack` holds something else, perhaps some non-trivial, >> unrelated, possibly "heavy" type, which just happens to be implicitly >> convertible from `int`. >> >> For `T == int` the difference between the variants would be purely >> conceptual, without any practical consequences. >> >> For a "heavy" `T` the difference between these two variants can be >> substantial. `push` would construct a temporary followed by two moves >> from it into a new container entry, while `emplace` would construct a >> new container entry in-place from the twice-forwarded `30`. > > That doesn't make the question "meaningless", nor does it prevent the > question from having an answer. The question can be answered in full by > quoting what the standard says about std::stack<T, Container>::push() > and emplace(). The ways in which the behavior depends upon T and > Containter are completely determined by what the standard says about > those functions, directly or indirectly. The "significant difference" > between those two functions that the OP was talking about consists > entirely of the differences between what the standard says about them, > along with the T-dependent implications of those differences. This is just another way of saying that every C++ question can be answered by a copy-paste of a link to the language standard. True, but not very useful. Linking to a specific section does not change much from qualitative point of view. I'm confident that the OP meant to ask a very specific question and expected to receive a very specific answer. Namely, the OP probably assumed that we'll immediately "deduce" `myStack` as `std::stack<int>`. I'm just pointing out the fact that this is an unjustified assumption. When asking questions, don't assume. Strive to provide all relevant information. Yes, sometimes it is difficult to properly include every important detail at the first try. But what we got here is ridiculously insufficient. -- Best regards, Andrey Tarasevich
[toc] | [prev] | [standalone]
Back to top | Article view | comp.lang.c++
csiph-web