6

「goto」ステートメントを使用してループから抜け出すにはどうすればよいですか

for(i = 0; (i < 9); i++)
    {
        for(j = 0; j < 9; j++)
        {
            //cout << " " << Matrix[i][j];
            //cout << "i: " << i << endl;
            if(Matrix[i][j] == 0)
            {
                //temp = 10;
                [goto] ;
                //break;
            }
        }
    }

ネストされた for ループを終了したときの i と j の値を維持したかったのです。そのためにgotoステートメントを使用するにはどうすればよいですか?

4

4 に答える 4

12

このような:

int i,j;
for(i = 0; i < 9; i++)
{
    for(j = 0; j < 9; j++)
    {
        //cout << " " << Matrix[i][j];
        //cout << "i: " << i << endl;
        if(Matrix[i][j] == 0)
        {
            //temp = 10;
            goto end;
            //break;
        }
    }
}
end:
cout << i << " " << j << endl;
于 2012-09-27T00:49:11.193 に答える
6

goto他の状況で使用するのと同じように。ローカル変数を含むスコープを超えない限り、実際には「これとその行に移動する」と考えることができます。

for (/* ... */) {
  /* ... */
  if (/* ... */)
    goto finalise;
}
finalise:
  foo = bar; //...

ただし、goto適切に設計されていないコードの指標となる状況は数多くあります。常にではありませんが、頻繁に。

gotos 兄貴を使用returnして、コードを関数に分解することをお勧めします。

inline std::pair<int,int> findZeroEntry(std::vector matrix) {
  for (int i = 0; i < 9; i++)
    for (int j = 0; j < 9; j++)
      if (Matrix[i][j] == 0)
        return std::make_pair(i,j);
  return std::make_pair(9,9); // error
}
于 2012-09-27T00:49:38.743 に答える
2

まあ、@bitmaskの答えは、質問を読んだときに私が考えていたことのほとんどをすでに述べています。

しかし、完全を期すために、別のテクニックを次に示します。

Matrix              m;
Index2D< 9, 9 >     pos;

for( ; pos < pos.end();  ++pos )
{
    if( m( pos.x(), pos.y() ) == 0 )
    {
        break;
    }
}
cout << pos.x() << " " << pos.y() << endl;

私見これははるかに明確なコードです。

また、マトリックスは、値を介したインデックス付けをサポートするように作成Index2Dできるため、上記を単に…に減らすことができます。

Matrix              m;
Index2D< 9, 9 >     pos;

for( ; pos < pos.end();  ++pos )
{
    if( m[pos] == 0 )
    {
        break;
    }
}
cout << pos.x() << " " << pos.y() << endl;

標準ライブラリには何もないのでIndex2D、どこかで定義する必要があります。

template< int width, int height >
struct Index2D
{
    int         i_;

    int x() const { return i_ % width; }
    int y() const { return i_ / width; }

    void operator++() { ++i_; }

    bool operator<( Index2D const& other ) const
    {
        return (i_ < other.i_);
    }

    Index2D(): i_( 0 ) {}

    Index2D( int const x, int const y )
        : i_( width*y + x )
    {}

    static const Index2D endValue;
    static Index2D end() { return endValue; }
};

template< int width, int height >
Index2D< width, height > const Index2D< width, height >::endValue( 0, height );

ただし、この機能が必要な場所ならどこでも再利用できます。

于 2012-09-27T02:06:54.743 に答える
1

gotoネストされた for ループを離れて、それらの変数を保存する必要はありません。単に、各ループから連続して抜け出したいだけです。ループから抜け出す必要があるかどうかを確認するために、適切なスコープ レベルでブール値を設定するだけです。

修正例

いいえ:

bool HasFoundZero = false;
for(i = 0; i < 9; i++)
{
    for(j = 0; j < 9; j++)
    {
        //cout << " " << Matrix[i][j];
        //cout << "i: " << i << endl;
        if(Matrix[i][j] == 0)
        {
            //temp = 10;
                HasFoundZero = true;
        }
        if(HasFoundZero)
        {
            break;
        }
    }
    if(HasFoundZero)
    {
        break;
    }
}
于 2012-09-27T00:48:40.897 に答える