1

I have defined a struct in side a class. One of the members is an array with a given size.

class foo {
private:
  int N;
  struct entry {
    uint64_t pc;
    uint64_t offset;
    bool pattern [N];
  };
public:
  void bar()
  {
   entry en;
   en.pc = 1;
   en.offset = 2;
   en.pattern[en.pc] = 1;
  }
};

But the error is

error: invalid use of non-static data member ‘N’
1
  • 1
    That's no a fixed-size array at all. Commented Oct 31, 2012 at 12:48

5 Answers 5

4

C++ doesn't support variable-length arrays. N must be known at compile-time. An alternative is using a std::vector instead.

class foo {
private:
  int N;
  struct entry {
    uint64_t pc;
    uint64_t offset;
    std::vector<int> pattern;
  };
public:
  void bar()
  {
   N = 100; //don't forget to initialize N
   entry en;
   en.pc = 1;
   en.offset = 2;
   en.pattern.resize(N);
   en.pattern[en.pc] = 1;
  }
};
Sign up to request clarification or add additional context in comments.

4 Comments

that pattern is a bit vector. let say 00000. Then I want to set one of them using en.pc to . So 01000. Using vector, I have to push_back
@mahmood you don't have to push_back using a vector. Also, you can use a std::bitset<N> instead.
Still using std::bitset I have to define a static const int N=5;
@mahmood yes, that's true. Then std::vector. You can create a vector with N entries and then use operator[] just as if it was an array. No push_back, no re-allocation.
2

N size have to be known at compile time. If you make in like static const int N=5 it will compile.

1 Comment

I corrected this for use in class. I typically use fixed size arrays on stack to perform some on side operations. I have never used it as class member.
2

To initialize an array, you must use a compile-time known integral constant. If you'd said static const int N=10;, say it would have worked.

Variable-length arrays, i.e. where the size is not known until runtime, are not allowed in C++.

One other way of doing this could be to use a template, e.g.:

template<int N>
struct my_struct {
    bool vals[N];
};

Or, similarly, use std::array, as in std::array<bool,10> vals;.

Comments

1

Better to use a std::vector than a fixed length array in most cases. In this case you don't know the size at compile time which isn't allowed anyway. Given that it's a collection of bool, you might want to consider a std::bitset which is a lot more size efficient than an array of bool

template < int S >
class foo {
private:
  int N;
  struct entry {
    uint64_t pc;
    uint64_t offset;
    std::bitset<S> pattern;
  };
public:
  entry en;
  foo()
  {
    en.pc = 1;
    en.offset = 2;
    en.pattern[en.pc] = 1;
  }
};

Note that I've added the foo constructor, which may or may not now make sense given the switch to a bitset, and the object can now be used as follows:

foo<24> myBits;

Comments

0

Here the N is not known at the compile time. if you create a ob1,ob2,ob3 then there is a possiblity that all the three object might have different value of N and which is against law of c++( variable-length arrays).

either use const int N=5; or make a N as class variable static int foo::N=6;

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.