Assigning to an array of 2D arrays from within a function using "std::copy"

I have an array of 2D arrays which I'm trying to initialise from within a function

I'm doing this for a simple board game I'm trying to make, which has three layers.

I understand you cannot directly assign an array to an array in C++, and that you should use std::copy. Unfortunately I'm having trouble trying to figure out how to implement this.

Here's a simplified version of my program to show what I'm trying to do:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
#include <iostream>
#include <string>
#include <iterator>

using namespace std;

typedef int layer[3][3];

typedef layer board[3];

void initTotal(board * example)
{
    layer thisLayer;
    for(int count = 0; count < 3; count++)
    {
        for(int count2 = 0; count2 < 3; count2++)
        {
            for(int count3 = 0; count3 < 3; count3++)
            {
                thisLayer[count2][count3] = 0;
                // In my actual program, it's much more complicated here.
                // Each element of thisLayer is a struct of enums, different for each element
            }
        }
        // *(example + count) = thisLayer;
        // If it were possible to assign to arrays, this is what I'd do here.

        copy(begin(thisLayer), end(thisLayer), example + count)
        // This is where the error occurs
    }
}

int main()
{
    board example;
    initTotal(&example);
    return 0;
}


The error occurs at:
copy(begin(thisLayer), end(thisLayer), example + count)

This gets me:
//error: 'begin' was not declared in this scope.
//error: 'end' was not declared in this scope.

From what I understand, I have to write a function of the form:
std::copy(first element of thisLayer, last element of thisLayer, the beginning of the correct position in 'example').


I've googled it and I'm not the first to have this problem: http://stackoverflow.com/questions/19877454/c11-error-begin-is-not-a-member-of-std

A few other websites have people getting the same error using a range for loop, which doesn't apply to me.

I've included "iterator", I've used the std namespace, and I'm sure "thisLayer" is an array. None of those fix the problem though. I've rewritten them as "std::begin" and "std::end", but this gets me:
//Error: 'begin' is not a member of 'std'.
//Error: 'end' is not a member of 'std'.

what can I do here?
Thanks in advance.

Edit:
The full program can be found here:
https://github.com/Matulin/MlinConsole/blob/master/include/board.h
https://github.com/Matulin/MlinConsole/blob/master/src/board.cpp

Edit 2:
Problem solved by making:
typedef int layer[3][3];
typedef layer board[3];

into:
typedef int board[3][3][3];

I'm going to delete this question in an hour. I'm not going to do it immediately in case someone's already typing up an answer (edit 3: and as it turned out, someone was!).
Last edited on
In code above my first suggestion is that you get rid of the typedef statements on lines 7 and 9.

Edit in your full program I also suggest you get rid of the typedefs and fix any any warnings and errors:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
board.h|16|warning: ‘typedef’ was ignored in this declaration|
board.h|23|warning: ‘typedef’ was ignored in this declaration|
board.h|29|warning: ‘typedef’ was ignored in this declaration|
main.cpp||In function ‘bool initBoard(position (*)[3][3])’:|
main.cpp|5|warning: no previous declaration forbool initBoard(position (*)[3][3])’ [-Wmissing-declarations]|
main.cpp|5|warning: declaration of ‘totalBoard’ shadows a global declaration [-Wshadow]|
board.h|33|note: shadowed declaration is here|
main.cpp|56|error: lvalue required as left operand of assignment|
main.cpp||In function ‘void displayBoard()’:|
main.cpp|62|warning: no previous declaration forvoid displayBoard()’ [-Wmissing-declarations]|
main.cpp||In function ‘void placePiece()’:|
main.cpp|69|warning: no previous declaration forvoid placePiece()’ [-Wmissing-declarations]|
main.cpp||In function ‘void moveToken()’:|
main.cpp|78|warning: no previous declaration forvoid moveToken()’ [-Wmissing-declarations]|
main.cpp||In function ‘void checkResult()’:|
main.cpp|85|warning: no previous declaration forvoid checkResult()’ [-Wmissing-declarations]|


Note that the "shadowed" warnings are probably a big part of the problems.





Last edited on
Hi,

Ordinary arrays don't have iterators.

Consider using nested for loops like you already have. Why are there 3 levels of nesting for a 2 dimensional array? Due to the underlying complexity?

1
2
// In my actual program, it's much more complicated here.
                // Each element of thisLayer is a struct of enums, different for each element 


Sounds messy :+(
> Ordinary arrays don't have iterators.

A pointer to an element in a c-style array is a RandomAccessIterator
This gets me:
//error: 'begin' was not declared in this scope.
//error: 'end' was not declared in this scope.
std::begin and std::end are enabled by #include <iterator> which your code is missing. However, they cannot be used without some additional effort for 2d arrays.

See: http://stackoverflow.com/questions/26948099/stdcopy-for-multidimensional-arrays
A pointer to an element in a c-style array is a RandomAccessIterator


Ok, thanks for that - I just had a quick read at cppreference.

So it might have been more accurate to say that ordinary arrays don't have built in begin or end iterators, but STL containers do?

And it looks like it is possible for one to make their own iterator for any custom (non STL) home-grown container, including an ordinary c-style array?

If I was feeling outrageously confident, I would say there might be potential to make an iterator for what I call an Xmas tree ADT, here:

https://projecteuler.net/problem=18

Say, for some reason not related to that problem I wanted the sum of all the numbers. Possible? If nodes were connected sideways, as well as to their children / parents: it might be possible to traverse rows. That might be handy for getting the info into the ADT to start with.

Now, don't go writing any code :+D As much as all of us really appreciate your outstanding efforts, could I mention that I might like to have a go at these problems one day?

There is another example too: IIRC one starts in the middle of a large matrix; then moving anticlockwise in a spiral fashion, carry out some operation . IIRC accumulate the "corner values" each direction change. A bit more tricky: we have x and y values; will have to sort out what it means to increment the iterator. I mean I have figured out how to travel in a spiral: but what that means in terms of the iterators; I would have to ruminate on that for a bit :+) Ah! It's just a linked list, but with logic from the spiral movement to determine which number is inserted next. So I could use the list's iterator once everything is in.

Thanks again !!

Regards :+)
> what that means in terms of the iterators; I would have to ruminate on that for a bit

The underlying idea behind an iterator is that of a sequence: "a finite set of objects, all of the same type, in a strictly linear arrangement."

An iterator "points to" an object in a sequence, and is used much like one would use a pointer to iterate over elements in a c-style array.

Once we have formulated clear answers to these questions, writer an iterator is fairly trivial:
a. Where does the sequence begin?
b. How is the end of the sequence (one past the last object) to be represented?
c. How would an iterator keep track of the object in the sequence that it "points to"?
d. How do we move from one object in the sequence to he next object in the sequence?

Spoiler: an iterator which iterates over a finite sequence of prime numbers
http://coliru.stacked-crooked.com/a/27654d38cb4a2573
Ah, yes those were exactly the things I had in mind:

Ah! It's just a linked list, but with logic from the spiral movement to determine which number is inserted next. So I could use the list's iterator once everything is in.


Although the tricky part is determining which is the next value: what with going backwards and forwards across a Xmas tree, and doing spirals on a matrix - I don't see it as being trivial. A bit more complex than Next++ :+) , but not hugely difficult.

Well I suppose any sequential container will do. But maybe a separate list is looking convenient IMO for the path type problems, even though it might use node pointers from the original ADT. Or maybe the original ADT can maintain iterator checkpoints, along with a pointer to the next one.

Must go .... ZZZZZZzzzzzZZZZZzzzz......

Topic archived. No new replies allowed.