3

Preamble:
I know that there are quite some topics with the same or a similar title. Keep reading and you will understand my case.


New to C++ I'm currently reading a book that quite obviously has a corrupt example excercise.
My code

#include <iostream>

using namespace std;

struct Point {
    int x;
    int y;
};

int main(int argc, char const* argv[]) {

    Point p1{100, 200};

    auto [a, b] = p1;

    cout << "a = " << a << endl;
    cout << "b = " << b << endl;

    auto& [c, d] = p1;

    c += 50;
    d += 50;

    cout << "p1.x = " << p1.x << endl;
    cout << "p1.y = " << p1.y << endl;

    return 0;
}

is almost an exact copy of the book. I only splitted the original one line cout into two lines and used namespace std instead of std::. Other than that the code is exactly like the example in the book.

Just to be 100% sure I'm not just having a typo, I donwloaded the example file from the books website.
We both get the same errors:

structuredBinding.cpp: In function ‘int main(int, const char**)’:
structuredBinding.cpp:14:7: error: expected unqualified-id before ‘[’ token
  auto [a, b] = p1;
       ^
structuredBinding.cpp:16:20: error: ‘a’ was not declared in this scope
  cout << "a = " << a << endl;
                    ^
structuredBinding.cpp:17:20: error: ‘b’ was not declared in this scope
  cout << "b = " << b << endl;
                    ^
structuredBinding.cpp:19:8: error: expected unqualified-id before ‘[’ token
  auto& [c, d] = p1;
        ^
structuredBinding.cpp:19:8: error: expected initializer before ‘[’ token
structuredBinding.cpp:21:2: error: ‘c’ was not declared in this scope
  c += 50;
  ^
structuredBinding.cpp:22:2: error: ‘d’ was not declared in this scope
  d += 50;
  ^

The book assumes its example exercise to work, but it doesn't.
I found some other topics regarding this or similar errors but none of them seem to work for me.

I also looked up the errata but there is no error registered for that part of the book.

I'm on Linux (Xubuntu) and I compile with g++ -std=c++17 -o <outputname> <inputname.cpp>

Can someone tell me what is wrong here? I would then report that error to the author.

Kuba hasn't forgotten Monica
  • 95,931
  • 16
  • 151
  • 313
antimatter
  • 63
  • 1
  • 10
  • 1
    Thats a fairly recent c++17 feature - structured bindings. Make sure you're running a c++17 compiler and that its in c++17 mode. – Mike Vine Feb 14 '18 at 23:42
  • That syntax is supported in C++17. Q1. Does your compiler support the C++17 standard? Q2. Did you use the appropriate compiler settings to instruct your compiler to use the C++17 standard for compiling? – R Sahu Feb 14 '18 at 23:42
  • 1
    It looks like you're using VS from the error style. Make sure you're running at least VS2017 Update 3 (compiler v19.11.25503) – Mike Vine Feb 14 '18 at 23:44
  • 8
    "used namespace std instead of std::" - Bad change! The book is trying to show you good habits. https://stackoverflow.com/questions/1452721/why-is-using-namespace-std-considered-bad-practice – aschepler Feb 14 '18 at 23:44
  • Yup, the code works with [GCC 7.2](https://wandbox.org/permlink/tOQQZGGxfEyphiyG). – Arnav Borborah Feb 15 '18 at 00:17
  • You need compiler flag `/std:c++17`. – jwdonahue Feb 15 '18 at 00:22

1 Answers1

5

To take advantage of C++17 features in GCC, you need to pass -std=c++17 on the compiler command line (e.g. by setting CXXFLAGS in your Makefile).

However, not all versions of GCC support all of the C++17 standard.

According to C++ Standards Support in GCC, you need at least g++ 7 to take advantage of structured bindings, and g++ 8 to take advantage of structured bindings to accessible members (e.g. private members from friend functions, rather than only public members).

Ubuntu 16.04 has g++ 5.4, Ubuntu 18.04 has g++ 7.3. To install a newer version of g++ on Ubuntu, see Install gcc-8 only on Ubuntu 18.04? (which applies to Ubuntu 16.04 as well) on Ask Ubuntu, particularly this answer.

I just installed gcc-8 and g++-8 packages on my Ubuntu 16.04 system, and structured bindings are now working fine.

Roger Lipscombe
  • 89,048
  • 55
  • 235
  • 380