complex stream extraction underspecifiedSection: 29.4.6 [complex.ops] Status: New Submitter: Tim Song Opened: 2016-05-23 Last modified: 2018-10-16
Priority: 3
View all other issues in [complex.ops].
View all issues with New status.
Discussion:
The specification of operator>>(istream&, complex<T>&) is extremely short on details.
It currently reads, in its entirety (29.4.6 [complex.ops]/12-15):
template<class T, class charT, class traits> basic_istream<charT, traits>& operator>>(basic_istream<charT, traits>& is, complex<T>& x);Effects: Extracts a complex number
Requires: The input values shall be convertible toxof the form:u,(u), or(u,v), whereuis the real part andvis the imaginary part (31.7.5.3 [istream.formatted]).T. If bad input is encountered, callsis.setstate(ios_base::failbit)(which may throwios::failure(31.5.4.4 [iostate.flags])). Returns:is. Remarks: This extraction is performed as a series of simpler extractions. Therefore, the skipping of whitespace is specified to be the same for each of the simpler extractions.
It is completely unclear:
'(', ')' and ','
(by ==, or by traits::eq),"(0, 0]", libstdc++ extracts the ]
while libc++ leaves it in the stream.)Previous resolution [SUPERSEDED]:
Drafting note: the following wording is based on:
- Characters are extracted using
operator>>and compared usingtraits::eq.- Mismatched characters are returned to the stream.
This wording is relative to N4582.
Replace 29.4.6 [complex.ops]/12-15 with the following paragraphs:
template<class T, class charT, class traits> basic_istream<charT, traits>& operator>>(basic_istream<charT, traits>& is, complex<T>& x);-?- Effects: First, extracts a character from
is.In the description above, characters are extracted from
- If the character extracted is equal to
is.widen('('), extracts an objectuof typeTfromis, then extracts a character fromis.
- If this character is equal to
is.widen(')'), then assignscomplex<T>(u)tox.- Otherwise, if this character is equal to
is.widen(','), extracts an objectvof typeTfromis, then extracts a character fromis. If this character is equal tois.widen(')'), then assignscomplex<T>(u, v)tox; otherwise returns the character toisand the extraction fails.- Otherwise, returns the character to
isand the extraction fails.- Otherwise, returns the character to
is, extracts an objectuof typeTfromis, and assignscomplex<T>(u)tox.isas if byoperator>>(31.7.5.3.3 [istream.extractors]), and returned to the stream as if bybasic_istream::putback(31.7.5.4 [istream.unformatted]). Character equality is determined usingtraits::eq. An objecttof typeTis extracted fromisas if byis >> t. If any extraction operation fails, no further operation is performed and the whole extraction fails. On failure, callsis.setstate(ios_base::failbit)(which may throwios::failure(31.5.4.4 [iostate.flags])). -?- Returns:is. -?- [Note: This extraction is performed as a series of simpler extractions. Therefore, the skipping of whitespace is specified to be the same for each of the simpler extractions. — end note]
[2017-12-13 Tim Song adjusts the P/R to avoid relying on putback.]
Proposed resolution:
Drafting note: the following wording assumes that:
- Characters are extracted using
operator>>and compared usingtraits::eq.- Mismatched characters are not extracted.
xis assigned a value-initializedcomplexon failure for consistency with the arithmetic extractors (compare LWG 696).
This wording is relative to N4778.
Replace 29.4.6 [complex.ops]/12-16 with the following paragraphs:
template<class T, class charT, class traits> basic_istream<charT, traits>& operator>>(basic_istream<charT, traits>& is, complex<T>& x);-?- Effects: Let
PEEK(is)be a formatted input function (31.7.5.3.1 [istream.formatted.reqmts]) ofisthat returns the next character that would be extracted fromisbyoperator>>. [Note: Thesentryobject is constructed and destroyed, but the returned character is not extracted from the stream. — end note]In the description above, characters are extracted from
- If
PEEK(is)is not equal tois.widen('('), extracts an objectuof typeTfromis, and assignscomplex<T>(u)tox.- Otherwise, extracts that character from
is, then extracts an objectuof typeTfromis, then:
- If
PEEK(is)is equal tois.widen(')'), then extracts that character fromisand assignscomplex<T>(u)tox.- Otherwise, if it is equal to
is.widen(','), then extracts that character fromisand then extracts an objectvof typeTfromis, then:
- If
PEEK(is)is equal tois.widen(')'), then extracts that character fromisand assignscomplex<T>(u, v)tox.- Otherwise, the extraction fails.
- Otherwise, the extraction fails.
isas if byoperator>>(31.7.5.3.3 [istream.extractors]), character equality is determined usingtraits::eq, and an objecttof typeTis extracted fromisas if byis >> t. If any extraction operation fails, no further operation is performed and the whole extraction fails. On failure, assignscomplex<T>()toxand callsis.setstate(ios_base::failbit)(which may throwios::failure(31.5.4.4 [iostate.flags])). -?- Returns:is. -?- [Note: This extraction is performed as a series of simpler extractions. Therefore, the skipping of whitespace is specified to be the same for each of the simpler extractions. — end note]