3

私はこれに似た問題を解決しようとしています:カードを捨てる。私の問題の唯一の変更点は、破棄されたカードのシーケンスが必要ないことです。最後に残ったカードだけが欲しい。

#include <iostream>
#include <cstdio>
#include <vector>
using namespace std;
int main(void)
{
    int n, i;
    while ((scanf ("%d", &n) == 1) && n != 0)
    {
        vector<int> cards;
        for (i = 1; i <= n; ++i)
        {
            cards.push_back(i);
        }
        while (cards.size() != 1)
        {
            cards.erase(cards.begin());
            cards.push_back(cards.front());
        }
        printf ("%d\n", cards.at(1));
    }
    return 0;
}

vector関連するすべての STL 関数を使用するのはこれが初めてです。これを確認したところ、このerase関数はベクター要素を削除すると書かれています。したがって、ループはになるまでwhileのサイズを減らし続ける必要があります。しかし、これを実行しても出力が得られません。無限ループが原因だと思うので、各反復でのサイズを印刷してみましたが、サイズが1回だけ縮小されていることがわかりました。したがって、これは無限ループを引き起こしています。しかし、なぜそれがさらに削減されないのか理解できません。vector1vector

4

3 に答える 3

2

フロント カードを移動せずにベクトルの最後にコピーするため、ベクトルのサイズが 1 に落ちることはありません。cards.push_back(cards.front())サイズを1つ大きくします。前のカードを vector の後ろに移動することが目的の場合は、2 つの行を交換します。

    while (cards.size() != 1)
    {
        cards.push_back(cards.front());
        cards.erase(cards.begin());
    }

もちろん、これはサイズを小さくしません。

編集: これは、フロント カードを削除し、次のカードをデッキ (ベクトル) の一番下に移動する提案されたソリューションです。

    while (cards.size() != 1)
    {
        cards.erase(cards.begin());
        cards.push_back(cards.front());
        cards.erase(cards.begin());
    }

サイズは、反復ごとに実質的に 1 ずつ減少します。

于 2013-10-19T17:58:46.463 に答える