web-dev-qa-db-fra.com

Remplir un vecteur de paires

Je veux remplir un vecteur avec 8 paires. Chaque paire représente les mouvements dans les coordonnées x et y qu'un chevalier peut jouer dans une partie d'échecs. En ce moment je le fais comme ça

vector<pair<int,int>> moves;

pair<int,int> aPair;
aPair.first = -2;
aPair.second = -1;
moves.Push_back(aPair);
aPair.first = -2;
aPair.second = 1;
moves.Push_back(aPair);
aPair.first = -1;
aPair.second = -2;
moves.Push_back(aPair);
aPair.first = -1;
aPair.second = 2;
moves.Push_back(aPair);
aPair.first = 1;
aPair.second = -2;
moves.Push_back(aPair);
aPair.first = 1;
aPair.second = 2;
moves.Push_back(aPair);
aPair.first = 2;
aPair.second = -1;
moves[6].Push_back(aPair);
aPair.first = 2;
aPair.second = 1;
moves.Push_back(aPair); 

Je le fais pour en savoir plus sur la bibliothèque Std. Cela semble être une façon désespérément inefficace de résoudre ce problème.

Quelqu'un a une solution plus élégante? 

15
Q-bertsuit

Des boucles à la rescousse:

for(int k = 0; k < 2; k++)
    for(int i = -1; i < 2; i += 2)
        for(int j = -1; j < 2; j+= 2)
            result.Push_back(make_pair(i * (k+1), j * (((k + 1) % 2) + 1)));

Sortie: http://ideone.com/2B0F9b

13
hate-engine

Si vous avez C++ 11 (sinon vous ne pouvez pas écrire >>), vous pouvez utiliser les éléments suivants:

vector<pair<int,int>> moves = {
  {-2, -1},
  {-2,  1},
  {-1, -2},
  {-1,  2},
  { 1, -2},
  { 1,  2},
  { 2, -1},
  { 2,  1}
};
16
ipc

En C++ 98/03:

moves.Push_back(std::make_pair(-2, -1));

En C++ 11:

moves.emplace_back(-2, -1);

Alternativement en C++ 11:

std::vector<std::pair<int, int>> moves = { { -2, -1}, ... };
9
Kerrek SB

Si vous n'avez pas C++ 11, vous pouvez utiliser make_pair , pré-allouer l'espace pour le vecteur sans initialiser les éléments à l'aide de la réserve, puis utiliser Push_back sans nouvelle affectation.

Par exemple:

vector<pair<int,int> > moves;
moves.reserve(8);
moves.Push_back(make_pair(-2, -1));
    // and so on

Même si vous avez C++ 11, cette technique est utile si vous devez calculer les éléments à la volée plutôt que de les coder en dur.

6
Josh Heitzman

Essayez ça:

vector<pair<int,int>> moves{{-2, -1}, {2, 1}, {-1, -2}, {-1, 2},
                            {1, -2},  {1, 2}, {2, -1},  {2, 1}};

La liste des initialiseurs avec l’initialisation uniforme donne beaucoup de puissance en C++ 11.

3
Mateusz Pusz

Voici une autre méthode pour faire la même chose.

template <class VectorClass>
class CreateVector
{
public:
    typedef typename VectorClass::value_type value_type;
    CreateVector(const value_type& value)
    {
        mVector.Push_back(value);
    }

    CreateVector& operator()(const value_type& value)
    {
        mVector.Push_back(value);
        return *this;
    }

    inline operator VectorClass() const
    {
        return mVector;
    }
private:
    VectorClass mVector;
};

Usage:

vector<pair<int,int>> moves = CreateVector<vector<pair<int,int> > >
(make_pair(1,2))
(make_pair(2,3))
(make_pair(3,4))
(make_pair(4,5));

EDIT: à condition que vous n'utilisiez pas C++ 11, ce serait un moyen. Sinon, je suggérerais de suivre le chemin suggéré par @ipc.

1
Vite Falcon

Si vous utilisez C++ 11, vous voudrez peut-être envisager std :: array au lieu de std :: vector. Comme un tableau normal, le tableau std a un nombre fixe d’éléments et a plus de sens conceptuel si vous savez à l’avance combien de données vous utilisez.

0
Alexander Duchene

Espérons une version plus lisible avec des boucles:

vector<pair<int, int>> result;
for(int moveX=1; moveX<=2; moveX++)
{
    for(int signX=-1; signX<=1; signX+=2)
    {
        for(int signY=-1; signY<=1; signY+=2)
        {
            result.Push_back(make_pair(moveX*signX, (3-moveX)*signY));
        }
    }
}

Programme complet produit le vecteur suivant:

{-1, -2},
{-1, 2},
{1, -2},
{1, 2},
{-2, -1},
{-2, 1},
{2, -1},
{2, 1},
0
Serge Rogatch