0

I would like to take a previously initialized array of objects and be able to set that to a class variable.

I don't have a lot of experience with pointers or great coding style.

This is a snippet of the code that I'm working on which isolates the problem:

#include<cstdlib>
#include<iostream>

using namespace std;

class GameBoard {
        string players[];
        int total_players;
    public:
        GameBoard (string given_players[]) {
            players = given_players;
            total_players = sizeof(given_players)/sizeof(*given_players);
        }
};

int main () {
    string players[] = {
        "Jack",
        "Jill"
    };
    GameBoard gb(players);
    return 0;
}

Currently, this code out puts the error:

In constructor 'GameBoard::GameBoard(std::string*)':
[Error] incompatible types in assignment of 'std::string* {aka std::basic_string<char>*}' to 'std::string* [0] {aka std::basic_string<char>* [0]}'
Cole Lawrence
  • 615
  • 6
  • 13
  • 3
    It would be easier if you used a copyable type, such as `std::vector`, instead of an array. Also, your `sizeof` calculation is wrong. And you need to `#include `. – juanchopanza Jan 27 '15 at 20:52
  • @ColeLawrence how do you propose the compiler to know the size of given_players? All it knows is that it's an array, but doesn't know the size. Therefore, arrays are not copyable. – inetknght Jan 27 '15 at 20:54
  • @inetknght Arrays are not copyable or assignable, even if you know the size (which, for real arrays, is easy enough to obtain.) – juanchopanza Jan 27 '15 at 20:56
  • @juanchopanza Okay, I'll pass in a `int size` parameter instead of trying to calculate it. Then, should I just use a pointer inside my class for `players`? – Cole Lawrence Jan 27 '15 at 20:57
  • 1
    I already made a good suggestion. If you want to disregard it, that's fine with me! – juanchopanza Jan 27 '15 at 20:58
  • @juanchopanza it isn't that I want to disregard it, it's that I honestly have never seen a vector in use before, and did not immediately understand your proposal. – Cole Lawrence Jan 27 '15 at 21:03
  • @juanchopanza does a vector work for other classes than std::string? – Cole Lawrence Jan 27 '15 at 21:05
  • 1
    @ColeLawrence No problem. See doc's solution. A vector is a class template. That means you can use it to make a class to hold elements of a given type. `vector` is a class that holds strings. `vector` holds doubles, and so on. – juanchopanza Jan 27 '15 at 21:07

1 Answers1

3

Better way of doing this

#include <vector>
#include <string>

class GameBoard {
    std::vector<std::string> players;
    int total_players;
public:
    GameBoard (const std::vector<std::string> & p_players):
        players(p_players),
        total_players(p_players.size())
    {
    }
};

then

int main()
{
    std::vector<std::string> players{"jill", "bill"}; //if C++11 is not available you can use push_back()
    GameBoard b{players};
    return 0;
 }
mip
  • 8,355
  • 6
  • 53
  • 72
  • Either pass `p_players` by const reference, or move it for initialization of `players`. The latter is the better option. – Mikhail Jan 27 '15 at 21:00
  • @Mikhail O.K. changed it to be oldschool, but take a look plz http://stackoverflow.com/questions/24543330/when-is-const-reference-better-than-pass-by-value-in-c11 – mip Jan 27 '15 at 21:04
  • Answers to this questions are very shallow. See "Effective Modern C++" by Scott Meyers, Item 41. It elaborates this topic in great detail. In the narrow case of constructor arguments with cheap to move type, you should always prefer passing by value + moving over passing by const reference + copying. – Mikhail Jan 27 '15 at 22:22
  • @Mikhail ah I see what you mean. `players(p_players)` would not invoke move constructor. – mip Jan 27 '15 at 23:05