How does the number of braces affect uniform initialization?
Consider the following code snippet:
#include <iostream>
struct A {
A() {}
A(const A&) {}
};
struct B {
B(const A&) {}
};
void f(const A&) { std::cout << "A" << std::endl; }
void f(const B&) { std::cout << "B" << std::endl; }
int main() {
A a;
f( {a} ); // A
f( {{a}} ); // ambiguous
f( {{{a}}} ); // B
f({{{{a}}}}); // no matching function
}
Why does each call fabricate the corresponding output? How does the number of braces affect uniform initialization? And how does brace elision affect all this?
c++ c++11 language-lawyer uniform-initialization brace-initialization
|
show 4 more comments
Consider the following code snippet:
#include <iostream>
struct A {
A() {}
A(const A&) {}
};
struct B {
B(const A&) {}
};
void f(const A&) { std::cout << "A" << std::endl; }
void f(const B&) { std::cout << "B" << std::endl; }
int main() {
A a;
f( {a} ); // A
f( {{a}} ); // ambiguous
f( {{{a}}} ); // B
f({{{{a}}}}); // no matching function
}
Why does each call fabricate the corresponding output? How does the number of braces affect uniform initialization? And how does brace elision affect all this?
c++ c++11 language-lawyer uniform-initialization brace-initialization
Completely attracted. But I think you' d better post your complier message. :)
– Constructor
yesterday
@Constructor the comments give the error messages when compiling with (at least) g++, else what is written during the execution
– bruno
yesterday
3
may want to add the taglanguage-lawyer
– Eljay
yesterday
3
Nit: semicolons after member function definitions are pointless and let the uninitiated imagine things like all closing braces should get one.
– Davis Herring
yesterday
2
@Rakete1111: There are more uses for null statements than null declarations (that are not also statements).
– Davis Herring
yesterday
|
show 4 more comments
Consider the following code snippet:
#include <iostream>
struct A {
A() {}
A(const A&) {}
};
struct B {
B(const A&) {}
};
void f(const A&) { std::cout << "A" << std::endl; }
void f(const B&) { std::cout << "B" << std::endl; }
int main() {
A a;
f( {a} ); // A
f( {{a}} ); // ambiguous
f( {{{a}}} ); // B
f({{{{a}}}}); // no matching function
}
Why does each call fabricate the corresponding output? How does the number of braces affect uniform initialization? And how does brace elision affect all this?
c++ c++11 language-lawyer uniform-initialization brace-initialization
Consider the following code snippet:
#include <iostream>
struct A {
A() {}
A(const A&) {}
};
struct B {
B(const A&) {}
};
void f(const A&) { std::cout << "A" << std::endl; }
void f(const B&) { std::cout << "B" << std::endl; }
int main() {
A a;
f( {a} ); // A
f( {{a}} ); // ambiguous
f( {{{a}}} ); // B
f({{{{a}}}}); // no matching function
}
Why does each call fabricate the corresponding output? How does the number of braces affect uniform initialization? And how does brace elision affect all this?
c++ c++11 language-lawyer uniform-initialization brace-initialization
c++ c++11 language-lawyer uniform-initialization brace-initialization
edited yesterday
user1494080
asked yesterday
user1494080user1494080
8002723
8002723
Completely attracted. But I think you' d better post your complier message. :)
– Constructor
yesterday
@Constructor the comments give the error messages when compiling with (at least) g++, else what is written during the execution
– bruno
yesterday
3
may want to add the taglanguage-lawyer
– Eljay
yesterday
3
Nit: semicolons after member function definitions are pointless and let the uninitiated imagine things like all closing braces should get one.
– Davis Herring
yesterday
2
@Rakete1111: There are more uses for null statements than null declarations (that are not also statements).
– Davis Herring
yesterday
|
show 4 more comments
Completely attracted. But I think you' d better post your complier message. :)
– Constructor
yesterday
@Constructor the comments give the error messages when compiling with (at least) g++, else what is written during the execution
– bruno
yesterday
3
may want to add the taglanguage-lawyer
– Eljay
yesterday
3
Nit: semicolons after member function definitions are pointless and let the uninitiated imagine things like all closing braces should get one.
– Davis Herring
yesterday
2
@Rakete1111: There are more uses for null statements than null declarations (that are not also statements).
– Davis Herring
yesterday
Completely attracted. But I think you' d better post your complier message. :)
– Constructor
yesterday
Completely attracted. But I think you' d better post your complier message. :)
– Constructor
yesterday
@Constructor the comments give the error messages when compiling with (at least) g++, else what is written during the execution
– bruno
yesterday
@Constructor the comments give the error messages when compiling with (at least) g++, else what is written during the execution
– bruno
yesterday
3
3
may want to add the tag
language-lawyer– Eljay
yesterday
may want to add the tag
language-lawyer– Eljay
yesterday
3
3
Nit: semicolons after member function definitions are pointless and let the uninitiated imagine things like all closing braces should get one.
– Davis Herring
yesterday
Nit: semicolons after member function definitions are pointless and let the uninitiated imagine things like all closing braces should get one.
– Davis Herring
yesterday
2
2
@Rakete1111: There are more uses for null statements than null declarations (that are not also statements).
– Davis Herring
yesterday
@Rakete1111: There are more uses for null statements than null declarations (that are not also statements).
– Davis Herring
yesterday
|
show 4 more comments
1 Answer
1
active
oldest
votes
Overload resolution is fun like this.
{a}has exact match rank for initializing (a temporary for) theconst A¶meter, which outcompetes the user-defined conversionB(const A&)as a realization of{a}. This rule was added in C++14 to resolve ambiguities in list-initialization (along with adjustments for aggregates).
Note that the notional temporary is never created: after overload resolution picks
f(const A&), the reference is simply initialized to refer toa, and this interpretation can apply even for non-copyable types.
- It would be permissible to initialize a
const A¶meter (as above) to the constructor for eitherAorB, so the call is ambiguous. - Calling a copy constructor (here,
A(const A&)) repeatedly is prohibited as multiple user-defined conversions—rather than allowing one such conversion per level of overload resolution. So the outermost braces must initialize aBfrom theAinitialized from{{a}}as (permitted) in the second case. (The middle layer of braces could initialize aB, but copying it with the outer layer would be prohibited and there’s nothing else to try to initialize.) - Every interpretation involves such a disallowed extra conversion.
No brace elision is involved—we don’t know the outermost target type to allow it.
Just to make sure that I understand it correctly:f({a})can be realized byf(A{a})orf(B{a}). Since the first is a perfect match, it is a better match than the second, and the call is unambiguous. Now we consider the second case.f({{a}})can be realized byf(A{A{a}}),f(B{A{a}}), andf(B{B{a}}). The first is prohibited and the second and the third are equally well matches, thus the call is ambiguous. Now consider the third case.f({{{a}}})can be realized byf(A{A{A{a}}}),f(B{A{A{a}}}),f(B{B{A{a}}}), andf(B{B{B{a}}}). Only the third is not prohibited.
– user1494080
yesterday
I think I haven't understood it yet. If the problem was thatf(B{A{a}})andf(B{B{a}})are equally well matches, the call would still be ambiguous when we removef(const A&). However, the compiler says the opposite.
– user1494080
yesterday
@user1494080: The ambiguity is betweenf(A{A{a}})(only the outer of those two is user-defined) andf(B{A{a}}).f(B{B{a}})is invalid because the inner conversion is user-defined and so the outer one must not be. Note the asymmetry:{a} -> Ais exact-match, but the resulting{B{a}} -> Bis user-defined because overload resolution had to occur to identify the{a} -> Bconversion.
– Davis Herring
yesterday
Doesn'tf(A{A{a}})call two times one and the same copy-constructorA(const A&)? How can one be user-defined and the other not?
– user1494080
yesterday
1
@DavisHerring Sorry, I’m still struggling.f(B{B{a}})is prohibited, because the inner conversion is user-defined (I agree), and the outer conversion is also user-defined (that's how I understand you). However, in the third case f(B{B{A{a}}}) is not prohibited, because the inner conversion is an exact match, the middle conversion is user-defined, and the outer one is again a standard conversion? Why is the firstf(B{B{...}})user-defined and the secondf(B{B{...}})not?
– user1494080
22 hours ago
|
show 10 more comments
Your Answer
StackExchange.ifUsing("editor", function () {
StackExchange.using("externalEditor", function () {
StackExchange.using("snippets", function () {
StackExchange.snippets.init();
});
});
}, "code-snippets");
StackExchange.ready(function() {
var channelOptions = {
tags: "".split(" "),
id: "1"
};
initTagRenderer("".split(" "), "".split(" "), channelOptions);
StackExchange.using("externalEditor", function() {
// Have to fire editor after snippets, if snippets enabled
if (StackExchange.settings.snippets.snippetsEnabled) {
StackExchange.using("snippets", function() {
createEditor();
});
}
else {
createEditor();
}
});
function createEditor() {
StackExchange.prepareEditor({
heartbeatType: 'answer',
autoActivateHeartbeat: false,
convertImagesToLinks: true,
noModals: true,
showLowRepImageUploadWarning: true,
reputationToPostImages: 10,
bindNavPrevention: true,
postfix: "",
imageUploader: {
brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
allowUrls: true
},
onDemand: true,
discardSelector: ".discard-answer"
,immediatelyShowMarkdownHelp:true
});
}
});
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f54504463%2fhow-does-the-number-of-braces-affect-uniform-initialization%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
1 Answer
1
active
oldest
votes
1 Answer
1
active
oldest
votes
active
oldest
votes
active
oldest
votes
Overload resolution is fun like this.
{a}has exact match rank for initializing (a temporary for) theconst A¶meter, which outcompetes the user-defined conversionB(const A&)as a realization of{a}. This rule was added in C++14 to resolve ambiguities in list-initialization (along with adjustments for aggregates).
Note that the notional temporary is never created: after overload resolution picks
f(const A&), the reference is simply initialized to refer toa, and this interpretation can apply even for non-copyable types.
- It would be permissible to initialize a
const A¶meter (as above) to the constructor for eitherAorB, so the call is ambiguous. - Calling a copy constructor (here,
A(const A&)) repeatedly is prohibited as multiple user-defined conversions—rather than allowing one such conversion per level of overload resolution. So the outermost braces must initialize aBfrom theAinitialized from{{a}}as (permitted) in the second case. (The middle layer of braces could initialize aB, but copying it with the outer layer would be prohibited and there’s nothing else to try to initialize.) - Every interpretation involves such a disallowed extra conversion.
No brace elision is involved—we don’t know the outermost target type to allow it.
Just to make sure that I understand it correctly:f({a})can be realized byf(A{a})orf(B{a}). Since the first is a perfect match, it is a better match than the second, and the call is unambiguous. Now we consider the second case.f({{a}})can be realized byf(A{A{a}}),f(B{A{a}}), andf(B{B{a}}). The first is prohibited and the second and the third are equally well matches, thus the call is ambiguous. Now consider the third case.f({{{a}}})can be realized byf(A{A{A{a}}}),f(B{A{A{a}}}),f(B{B{A{a}}}), andf(B{B{B{a}}}). Only the third is not prohibited.
– user1494080
yesterday
I think I haven't understood it yet. If the problem was thatf(B{A{a}})andf(B{B{a}})are equally well matches, the call would still be ambiguous when we removef(const A&). However, the compiler says the opposite.
– user1494080
yesterday
@user1494080: The ambiguity is betweenf(A{A{a}})(only the outer of those two is user-defined) andf(B{A{a}}).f(B{B{a}})is invalid because the inner conversion is user-defined and so the outer one must not be. Note the asymmetry:{a} -> Ais exact-match, but the resulting{B{a}} -> Bis user-defined because overload resolution had to occur to identify the{a} -> Bconversion.
– Davis Herring
yesterday
Doesn'tf(A{A{a}})call two times one and the same copy-constructorA(const A&)? How can one be user-defined and the other not?
– user1494080
yesterday
1
@DavisHerring Sorry, I’m still struggling.f(B{B{a}})is prohibited, because the inner conversion is user-defined (I agree), and the outer conversion is also user-defined (that's how I understand you). However, in the third case f(B{B{A{a}}}) is not prohibited, because the inner conversion is an exact match, the middle conversion is user-defined, and the outer one is again a standard conversion? Why is the firstf(B{B{...}})user-defined and the secondf(B{B{...}})not?
– user1494080
22 hours ago
|
show 10 more comments
Overload resolution is fun like this.
{a}has exact match rank for initializing (a temporary for) theconst A¶meter, which outcompetes the user-defined conversionB(const A&)as a realization of{a}. This rule was added in C++14 to resolve ambiguities in list-initialization (along with adjustments for aggregates).
Note that the notional temporary is never created: after overload resolution picks
f(const A&), the reference is simply initialized to refer toa, and this interpretation can apply even for non-copyable types.
- It would be permissible to initialize a
const A¶meter (as above) to the constructor for eitherAorB, so the call is ambiguous. - Calling a copy constructor (here,
A(const A&)) repeatedly is prohibited as multiple user-defined conversions—rather than allowing one such conversion per level of overload resolution. So the outermost braces must initialize aBfrom theAinitialized from{{a}}as (permitted) in the second case. (The middle layer of braces could initialize aB, but copying it with the outer layer would be prohibited and there’s nothing else to try to initialize.) - Every interpretation involves such a disallowed extra conversion.
No brace elision is involved—we don’t know the outermost target type to allow it.
Just to make sure that I understand it correctly:f({a})can be realized byf(A{a})orf(B{a}). Since the first is a perfect match, it is a better match than the second, and the call is unambiguous. Now we consider the second case.f({{a}})can be realized byf(A{A{a}}),f(B{A{a}}), andf(B{B{a}}). The first is prohibited and the second and the third are equally well matches, thus the call is ambiguous. Now consider the third case.f({{{a}}})can be realized byf(A{A{A{a}}}),f(B{A{A{a}}}),f(B{B{A{a}}}), andf(B{B{B{a}}}). Only the third is not prohibited.
– user1494080
yesterday
I think I haven't understood it yet. If the problem was thatf(B{A{a}})andf(B{B{a}})are equally well matches, the call would still be ambiguous when we removef(const A&). However, the compiler says the opposite.
– user1494080
yesterday
@user1494080: The ambiguity is betweenf(A{A{a}})(only the outer of those two is user-defined) andf(B{A{a}}).f(B{B{a}})is invalid because the inner conversion is user-defined and so the outer one must not be. Note the asymmetry:{a} -> Ais exact-match, but the resulting{B{a}} -> Bis user-defined because overload resolution had to occur to identify the{a} -> Bconversion.
– Davis Herring
yesterday
Doesn'tf(A{A{a}})call two times one and the same copy-constructorA(const A&)? How can one be user-defined and the other not?
– user1494080
yesterday
1
@DavisHerring Sorry, I’m still struggling.f(B{B{a}})is prohibited, because the inner conversion is user-defined (I agree), and the outer conversion is also user-defined (that's how I understand you). However, in the third case f(B{B{A{a}}}) is not prohibited, because the inner conversion is an exact match, the middle conversion is user-defined, and the outer one is again a standard conversion? Why is the firstf(B{B{...}})user-defined and the secondf(B{B{...}})not?
– user1494080
22 hours ago
|
show 10 more comments
Overload resolution is fun like this.
{a}has exact match rank for initializing (a temporary for) theconst A¶meter, which outcompetes the user-defined conversionB(const A&)as a realization of{a}. This rule was added in C++14 to resolve ambiguities in list-initialization (along with adjustments for aggregates).
Note that the notional temporary is never created: after overload resolution picks
f(const A&), the reference is simply initialized to refer toa, and this interpretation can apply even for non-copyable types.
- It would be permissible to initialize a
const A¶meter (as above) to the constructor for eitherAorB, so the call is ambiguous. - Calling a copy constructor (here,
A(const A&)) repeatedly is prohibited as multiple user-defined conversions—rather than allowing one such conversion per level of overload resolution. So the outermost braces must initialize aBfrom theAinitialized from{{a}}as (permitted) in the second case. (The middle layer of braces could initialize aB, but copying it with the outer layer would be prohibited and there’s nothing else to try to initialize.) - Every interpretation involves such a disallowed extra conversion.
No brace elision is involved—we don’t know the outermost target type to allow it.
Overload resolution is fun like this.
{a}has exact match rank for initializing (a temporary for) theconst A¶meter, which outcompetes the user-defined conversionB(const A&)as a realization of{a}. This rule was added in C++14 to resolve ambiguities in list-initialization (along with adjustments for aggregates).
Note that the notional temporary is never created: after overload resolution picks
f(const A&), the reference is simply initialized to refer toa, and this interpretation can apply even for non-copyable types.
- It would be permissible to initialize a
const A¶meter (as above) to the constructor for eitherAorB, so the call is ambiguous. - Calling a copy constructor (here,
A(const A&)) repeatedly is prohibited as multiple user-defined conversions—rather than allowing one such conversion per level of overload resolution. So the outermost braces must initialize aBfrom theAinitialized from{{a}}as (permitted) in the second case. (The middle layer of braces could initialize aB, but copying it with the outer layer would be prohibited and there’s nothing else to try to initialize.) - Every interpretation involves such a disallowed extra conversion.
No brace elision is involved—we don’t know the outermost target type to allow it.
edited 20 hours ago
answered yesterday
Davis HerringDavis Herring
8,4401635
8,4401635
Just to make sure that I understand it correctly:f({a})can be realized byf(A{a})orf(B{a}). Since the first is a perfect match, it is a better match than the second, and the call is unambiguous. Now we consider the second case.f({{a}})can be realized byf(A{A{a}}),f(B{A{a}}), andf(B{B{a}}). The first is prohibited and the second and the third are equally well matches, thus the call is ambiguous. Now consider the third case.f({{{a}}})can be realized byf(A{A{A{a}}}),f(B{A{A{a}}}),f(B{B{A{a}}}), andf(B{B{B{a}}}). Only the third is not prohibited.
– user1494080
yesterday
I think I haven't understood it yet. If the problem was thatf(B{A{a}})andf(B{B{a}})are equally well matches, the call would still be ambiguous when we removef(const A&). However, the compiler says the opposite.
– user1494080
yesterday
@user1494080: The ambiguity is betweenf(A{A{a}})(only the outer of those two is user-defined) andf(B{A{a}}).f(B{B{a}})is invalid because the inner conversion is user-defined and so the outer one must not be. Note the asymmetry:{a} -> Ais exact-match, but the resulting{B{a}} -> Bis user-defined because overload resolution had to occur to identify the{a} -> Bconversion.
– Davis Herring
yesterday
Doesn'tf(A{A{a}})call two times one and the same copy-constructorA(const A&)? How can one be user-defined and the other not?
– user1494080
yesterday
1
@DavisHerring Sorry, I’m still struggling.f(B{B{a}})is prohibited, because the inner conversion is user-defined (I agree), and the outer conversion is also user-defined (that's how I understand you). However, in the third case f(B{B{A{a}}}) is not prohibited, because the inner conversion is an exact match, the middle conversion is user-defined, and the outer one is again a standard conversion? Why is the firstf(B{B{...}})user-defined and the secondf(B{B{...}})not?
– user1494080
22 hours ago
|
show 10 more comments
Just to make sure that I understand it correctly:f({a})can be realized byf(A{a})orf(B{a}). Since the first is a perfect match, it is a better match than the second, and the call is unambiguous. Now we consider the second case.f({{a}})can be realized byf(A{A{a}}),f(B{A{a}}), andf(B{B{a}}). The first is prohibited and the second and the third are equally well matches, thus the call is ambiguous. Now consider the third case.f({{{a}}})can be realized byf(A{A{A{a}}}),f(B{A{A{a}}}),f(B{B{A{a}}}), andf(B{B{B{a}}}). Only the third is not prohibited.
– user1494080
yesterday
I think I haven't understood it yet. If the problem was thatf(B{A{a}})andf(B{B{a}})are equally well matches, the call would still be ambiguous when we removef(const A&). However, the compiler says the opposite.
– user1494080
yesterday
@user1494080: The ambiguity is betweenf(A{A{a}})(only the outer of those two is user-defined) andf(B{A{a}}).f(B{B{a}})is invalid because the inner conversion is user-defined and so the outer one must not be. Note the asymmetry:{a} -> Ais exact-match, but the resulting{B{a}} -> Bis user-defined because overload resolution had to occur to identify the{a} -> Bconversion.
– Davis Herring
yesterday
Doesn'tf(A{A{a}})call two times one and the same copy-constructorA(const A&)? How can one be user-defined and the other not?
– user1494080
yesterday
1
@DavisHerring Sorry, I’m still struggling.f(B{B{a}})is prohibited, because the inner conversion is user-defined (I agree), and the outer conversion is also user-defined (that's how I understand you). However, in the third case f(B{B{A{a}}}) is not prohibited, because the inner conversion is an exact match, the middle conversion is user-defined, and the outer one is again a standard conversion? Why is the firstf(B{B{...}})user-defined and the secondf(B{B{...}})not?
– user1494080
22 hours ago
Just to make sure that I understand it correctly:
f({a}) can be realized by f(A{a}) or f(B{a}). Since the first is a perfect match, it is a better match than the second, and the call is unambiguous. Now we consider the second case. f({{a}}) can be realized by f(A{A{a}}), f(B{A{a}}), and f(B{B{a}}). The first is prohibited and the second and the third are equally well matches, thus the call is ambiguous. Now consider the third case. f({{{a}}}) can be realized by f(A{A{A{a}}}), f(B{A{A{a}}}), f(B{B{A{a}}}), and f(B{B{B{a}}}). Only the third is not prohibited.– user1494080
yesterday
Just to make sure that I understand it correctly:
f({a}) can be realized by f(A{a}) or f(B{a}). Since the first is a perfect match, it is a better match than the second, and the call is unambiguous. Now we consider the second case. f({{a}}) can be realized by f(A{A{a}}), f(B{A{a}}), and f(B{B{a}}). The first is prohibited and the second and the third are equally well matches, thus the call is ambiguous. Now consider the third case. f({{{a}}}) can be realized by f(A{A{A{a}}}), f(B{A{A{a}}}), f(B{B{A{a}}}), and f(B{B{B{a}}}). Only the third is not prohibited.– user1494080
yesterday
I think I haven't understood it yet. If the problem was that
f(B{A{a}}) and f(B{B{a}}) are equally well matches, the call would still be ambiguous when we remove f(const A&). However, the compiler says the opposite.– user1494080
yesterday
I think I haven't understood it yet. If the problem was that
f(B{A{a}}) and f(B{B{a}}) are equally well matches, the call would still be ambiguous when we remove f(const A&). However, the compiler says the opposite.– user1494080
yesterday
@user1494080: The ambiguity is between
f(A{A{a}}) (only the outer of those two is user-defined) and f(B{A{a}}). f(B{B{a}}) is invalid because the inner conversion is user-defined and so the outer one must not be. Note the asymmetry: {a} -> A is exact-match, but the resulting {B{a}} -> B is user-defined because overload resolution had to occur to identify the {a} -> B conversion.– Davis Herring
yesterday
@user1494080: The ambiguity is between
f(A{A{a}}) (only the outer of those two is user-defined) and f(B{A{a}}). f(B{B{a}}) is invalid because the inner conversion is user-defined and so the outer one must not be. Note the asymmetry: {a} -> A is exact-match, but the resulting {B{a}} -> B is user-defined because overload resolution had to occur to identify the {a} -> B conversion.– Davis Herring
yesterday
Doesn't
f(A{A{a}}) call two times one and the same copy-constructor A(const A&)? How can one be user-defined and the other not?– user1494080
yesterday
Doesn't
f(A{A{a}}) call two times one and the same copy-constructor A(const A&)? How can one be user-defined and the other not?– user1494080
yesterday
1
1
@DavisHerring Sorry, I’m still struggling.
f(B{B{a}}) is prohibited, because the inner conversion is user-defined (I agree), and the outer conversion is also user-defined (that's how I understand you). However, in the third case f(B{B{A{a}}}) is not prohibited, because the inner conversion is an exact match, the middle conversion is user-defined, and the outer one is again a standard conversion? Why is the first f(B{B{...}}) user-defined and the second f(B{B{...}}) not?– user1494080
22 hours ago
@DavisHerring Sorry, I’m still struggling.
f(B{B{a}}) is prohibited, because the inner conversion is user-defined (I agree), and the outer conversion is also user-defined (that's how I understand you). However, in the third case f(B{B{A{a}}}) is not prohibited, because the inner conversion is an exact match, the middle conversion is user-defined, and the outer one is again a standard conversion? Why is the first f(B{B{...}}) user-defined and the second f(B{B{...}}) not?– user1494080
22 hours ago
|
show 10 more comments
Thanks for contributing an answer to Stack Overflow!
- Please be sure to answer the question. Provide details and share your research!
But avoid …
- Asking for help, clarification, or responding to other answers.
- Making statements based on opinion; back them up with references or personal experience.
To learn more, see our tips on writing great answers.
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f54504463%2fhow-does-the-number-of-braces-affect-uniform-initialization%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Completely attracted. But I think you' d better post your complier message. :)
– Constructor
yesterday
@Constructor the comments give the error messages when compiling with (at least) g++, else what is written during the execution
– bruno
yesterday
3
may want to add the tag
language-lawyer– Eljay
yesterday
3
Nit: semicolons after member function definitions are pointless and let the uninitiated imagine things like all closing braces should get one.
– Davis Herring
yesterday
2
@Rakete1111: There are more uses for null statements than null declarations (that are not also statements).
– Davis Herring
yesterday