Oracleシーケンスの現在の値をインクリメントせずに取得する方法は?


156

増分しないシーケンスの値を取得するSQL命令はありますか?

ありがとう。

編集と結論

Justin Caveが述べたように、シーケンス番号を「保存」しようとしても役に立たないので

select a_seq.nextval from dual;

シーケンス値をチェックするには十分です。

それが最初の質問に答えたので、私はまだオリーの答えを良いものとして保ちます。ただし、シーケンスを変更する必要がある場合は、変更しないことの必要性について自問してください。


5
どうして?解決しようとしている問題は何ですか?シーケンスを正しく使用している場合は、他のセッションに割り当てられているシーケンス値や、後続のセッションに割り当てられている可能性のある値を気にする必要はありません。
ジャスティンケイブ

3
移行されたデータに従ってシーケンスが正しく更新されていることを確認するための、データ移行後のチェック
frno

3
次にnextval、テストするシーケンスを単に取得することの欠点は何ですか?シーケンスにギャップがないとは想定していませんよね?したがって、シーケンス値を「無駄にする」ことは問題になりません。
ジャスティンケイブ

私はあなたが正しいと思いますが、私はそのチェックのためにデータベースの状態を変更したくありませんでしたが、正直なところ、理由はわかりません。あなたの洞察をありがとう。それでも私はシーケンスについてあなたのことを学びました、ありがとうございます!
frno

シーケンスの値を確実に取得できると仮定すると、シーケンスが適切に更新されていることを確認するオラクルは何ですか?
シャノン退職2012

回答:


173
SELECT last_number
  FROM all_sequences
 WHERE sequence_owner = '<sequence owner>'
   AND sequence_name = '<sequence_name>';

あなたはからのシーケンスのメタデータの多様性を得ることができuser_sequencesall_sequencesそしてdba_sequences

これらのビューはセッション全体で機能します。

編集:

シーケンスがデフォルトのスキーマにある場合:

SELECT last_number
  FROM user_sequences
 WHERE sequence_name = '<sequence_name>';

すべてのメタデータが必要な場合:

SELECT *
  FROM user_sequences
 WHERE sequence_name = '<sequence_name>';

それが役に立てば幸い...

EDIT2:

キャッシュサイズが1でない場合に、より信頼性の高い方法でこれを行うには、次のようになります。

SELECT increment_by I
  FROM user_sequences
 WHERE sequence_name = 'SEQ';

      I
-------
      1

SELECT seq.nextval S
  FROM dual;

      S
-------
   1234

-- Set the sequence to decrement by 
-- the same as its original increment
ALTER SEQUENCE seq 
INCREMENT BY -1;

Sequence altered.

SELECT seq.nextval S
  FROM dual;

      S
-------
   1233

-- Reset the sequence to its original increment
ALTER SEQUENCE seq 
INCREMENT BY 1;

Sequence altered.

この時間中に他の人がシーケンスを使用している場合は注意してください-彼ら(またはあなた)は

ORA-08004: sequence SEQ.NEXTVAL goes below the sequences MINVALUE and cannot be instantiated

また、NOCACHE多くの値がキャッシュされていないことを確認するために、リセットする前にキャッシュを設定し、後で元の値に戻すこともできます。


試してみましたが、「all_sequences」テーブルにアクセスできません。管理者資格情報でのみ表示される特別なオブジェクトですか?
frno 2012

1
ALL_SEQUENCESビューです。アクセス権がないUSER_SEQUENCES場合は、シーケンスがデフォルトのスキーマにあるかどうかを選択してみてください。(のsequence_owner = '<sequence_owner>'句は必要ありませんUSER_SEQUENCES)。
Ollie第

15
LAST_NUMBER中には、ALL_SEQUENCESセッションが実際に与えられたとの呼び出しから返される数ではないだろうという最後の番号ではありませんsequence_name.nextval一般的に。シーケンスをCACHE1以上(デフォルトは20)に設定したとLAST_NUMBERすると、はキャッシュ内の最後の数値になります。この番号が実際にセッションに割り当てられるという保証はありません。
ジャスティンケイブ

2
ALTER SEQUENCE seq INCREMENT BY -1;他のセッションが呼び出さないことを保証できない限り、問題になりますseq.nextval。それ以外の場合、シーケンスは重複した値を配布しますが、これは通常は必要ありません。
シャノン退職2012

1
OPは「データ移行後のチェックだ」と言っていたため、DBが一般的に使用されていないと想定するのは簡単ではありませんが、そうでない場合は問題になる可能性があります。
Ollie

122

select MY_SEQ_NAME.currval from DUAL;

select MY_SEQ_NAME.nextval from DUAL;現在のセッションで実行した場合にのみ機能することに注意してください。


1
あなたの答えをたくさんありがとう。私はこれをBoomiの中で使用しなければならず、解決策を上下に探していました
学習...

0

私の元の返信は事実上正しくなかったので、削除されてよかった。以下のコードは、次の条件で動作します。a)他の誰もシーケンスを変更していないことを知っているb)シーケンスがセッションによって変更された。私の場合、値を変更するプロシージャを呼び出すときに同様の問題が発生しましたが、この仮定が正しいと確信しています。

SELECT mysequence.CURRVAL INTO v_myvariable FROM DUAL;

残念ながら、セッションでシーケンスを変更しなかった場合、NEXTVALが唯一の方法であると他の人が言っているのは正しいと思います。


0

これは答えではありません。質問がロックされていなければ、コメントとして入力していました。これは質問に答えます:

なぜあなたはそれを望みますか?

シーケンスを主キーとするテーブルがあり、シーケンスは挿入トリガーによって生成されると想定します。レコードの後続の更新でシーケンスを使用できるようにする場合は、その値を抽出する方法が必要です。

正しいものを確実に取得するために、INSERTおよびRonKのクエリをトランザクションでラップすることができます。

RonKのクエリ:

select MY_SEQ_NAME.currval from DUAL;

上記のシナリオでは、挿入と更新が同じセッションで発生するため、RonKの警告は当てはまりません。


0

私の場合は、CURRVALを使用して、いくつかのプロセスがそのシーケンスを主キーとしてテーブルに新しい行を挿入したかどうかを確認することも試みました。私の仮定は、CURRVALが最速の方法であるということでした。ただし、a)CurrValは機能しません。別のOracleセッションにいるため、独自のセッションでNEXTVALを実行するまで、古い値が取得されます。b)a select max(PK) from TheTableも非常に高速です。これは、おそらくPKが常にインデックス付けされているためです。またはselect count(*) from TheTable。まだ実験中ですが、どちらのSELECTも高速に見えます。

シーケンスのギャップは気にしませんが、私の場合、ポーリングをたくさん考えていたので、非常に大きなギャップの考えは嫌いでした。特に、単純なSELECTが同じくらい高速である場合。

結論:

  • CURRVALは、別のセッションからのNEXTVALを検出しないため、ほとんど役に立ちません。以前のNEXTVALからすでに知っているものだけを返します。
  • SELECT MAX(...)FROM ...は、シーケンスがそのテーブルにリンクされていると仮定すると、シンプルで高速な優れたソリューションです
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.