0
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

WHILE文で無限ループにはまった(SQL SEVERの話)

Posted at

SQLのWHILE文で無限ループにはまった。

投稿の経緯

SQLでカーソルを使用して、カーソル内のデータについて処理する際に、
While文を用いて繰返し処理をしているのですが、そこで無限ループを起こしました
解決はしたものの、1時間以上つまずいくことに・・・
自戒を込めて原因と対処法について投稿します

※記事の間違い、もっと良いやり方があると言う方は教えていただけると嬉しいです

WHILE文とは

指定した条件が"True"を返す場合、処理を繰り返すことができる
基本構文は以下のとおりである

qiita.rb
WHILE "条件式"
BEGIN
  "繰り返したい処理"
TRY

WHILE "条件式" の下に繰返しの処理を"BEGIN"と"TRY"で書く。
このことを理解していれば、無限ループにはまることはなかっただろう。

環境

使用したDB
 ・SQL Sever Express 2016
  ※DBはサーバにあり、それをクライアントPCより操作していた。

無限ループが発生したWHILE文

以下が問題のSQLである。
目的の処理は
TableAからSelectした項目”A”をカーソルとして定義。(処理①)
定義したカーソルを開く(処理②)
処理①で取得したカーソルの1行目のデータをTableBへInesrtする(処理③)
ループ終了後、カーゾルを閉じて中身を消去する(処理④)
である。

qiita.rb
--処理➀
DECLARE Cur  CURSOR FOR
SELECT
 A --カラム名
FROM
  TableA

OPEN Cur --カーソルオープン

FETCH NEXT FROM Cur --処理➁
INTO
  @a

--処理③
WHILE @@FETCH_STATUS = 0
  --INSERT処理
BEGIN
    INSERT INTO
	TableB
	(
        A
	)
	VALUES
	(
	    @a
	)
END	
BEGIN 
  FETCH NEXT FROM Cur
    INTO
        @a
    ;
 END
END

CLOSE Cur--処理④
;
DEALLOCATE Cur
;

#結果
試しにSQLを実行してみたが、30分たっても終了しない
いくらカーソルを使用して繰り返しをしているとはいえ、
処理時間が長すぎる
そこで、無限ループしていることに気づいた

#原因
結論から言うとWhile文でループする範囲の指定を間違えたことにあった。
このSQLではWhileの下にあるBEGINがInsert文下のENDに対応しており、
次の行の取得がないため、
WHILE @@FETCH_STATUS = 0(カーソルの中身を取得できた場合0が返る)
を満たしつづけるため無限ループになっていた

qiita.rb
--処理③
WHILE @@FETCH_STATUS = 0
  --INSERT処理
BEGIN           --ここから
    INSERT INTO
	TableB
	(
        A
	)
	VALUES
	(
	    @a
	)
END	            --ここまでループ
BEGIN 
  FETCH NEXT FROM Cur
    INTO
        @a
    ;
END

ので、正しくは以下の通りに BEGINとENDを
正しく指定すればよい

qiita.rb
--処理③
WHILE @@FETCH_STATUS = 0
  --INSERT処理
BEGIN           --ここから
    INSERT INTO
	TableB
	(
        A
	)
	VALUES
	(
	    @a
	)

  FETCH NEXT FROM Cur
    INTO
        @a
    ;
END             --ここまでループ

#最後に
SQLを書く際には何も考えずに処理単位でBEGIN ENDを張っていたが
ちゃんと構文の形を理解しないと
思わぬところでハマると言う教訓になった出来事でした

0
1
2

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?