Следующий код имеет разные результаты компиляции.Судя по полученному сообщению об ошибке, возникает путаница относительно приоритета операторов ()
и <<
.Я могу легко преодолеть эту проблему с помощью функции.Однако я хотел бы понять и узнать:
a) Какой компилятор правильно оценивает выражение?MSVC2017 кажется мне более логичным.
b) Есть ли обходной путь, все еще использующий MACRO?
Полный пример кода, который я использовал.
#include <cstdlib>
#include <typeinfo>
#include <sstream>
#include <iostream>
#ifndef NDEBUG
#define EXPR_INSPECT(param_)\
( (std::ostringstream{} << "< " #param_ " [" << typeid(param_).name() << "] > : " << param_).str() )
#else
#define EXPR_INSPECT(param_)\
(param_)
#endif //NDEBUG
int main(int argc, char *argv[])
{
auto ull_x {99LLU};
std::string string_x {"Checking..."};
std::cout << EXPR_INSPECT( ull_x) << std::endl;
std::cout << EXPR_INSPECT(string_x) << std::endl;
return EXIT_SUCCESS;
}
MSVC2017 отлично работает!
G ++ 8.2.0 (MSYS2 / MINGW) выдает следующую ошибку: 'std :: basic_ostream :: __ ostream_type' {aka 'class std :: basic_ostream'} имеетнет члена с именем 'str' Попытки вызвать str()
на ostream
вместо ostringstream
.
РЕДАКТИРОВАТЬ:
Проблема здесь также может быть воспроизведена при помощи Wandbox .Вот минимальный пример:
#include <sstream>
#include <iostream>
int main()
{
auto s = std::ostringstream{};
decltype(((std::ostringstream{}) << "< "))::nothing;
decltype((s << "< "))::nothing;
}
В wandbox, clang обнаружил второй тип std::basic_ostream
, а первый тип std::basic_ostringstream
.Это очень странно.