私は Pythonのsqlite3モジュール (およびその点でのSQL全般)が初めてであり、これはまったく私を困らせます。 cursor
オブジェクト (むしろ、その必要性)の記述が豊富にないことも奇妙に思えます。
このコードスニペットは、物事を行うための好ましい方法です。
import sqlite3
conn = sqlite3.connect("db.sqlite")
c = conn.cursor()
c.execute('''insert into table "users" values ("Jack Bauer", "555-555-5555")''')
conn.commit()
c.close()
これは、(一見無意味な)cursor
なしでも同じように機能しますが、そうではありません:
import sqlite3
conn = sqlite3.connect("db.sqlite")
conn.execute('''insert into table "users" values ("Jack Bauer", "555-555-5555")''')
conn.commit()
cursor
が必要な理由を誰か教えてもらえますか?
それは無意味なオーバーヘッドのようです。データベースにアクセスするスクリプト内のすべてのメソッドについて、cursor
?を作成および破棄することになっています。
なぜconnection
オブジェクトを使用しないのですか?
単なる誤用の抽象化のように思えます。 dbカーソルは、データセットトラバーサルを目的とした抽象化です。
コンピュータサイエンスとテクノロジーでは、データベースカーソルは、データベース内のレコードを走査できるようにする制御構造です。カーソルは、データベースレコードの取得、追加、削除など、トラバーサルに関連する後続の処理を容易にします。トラバーサルのデータベースカーソルの特性により、カーソルはイテレータのプログラミング言語の概念に似ています。
そして:
カーソルは、DBMSからアプリケーションにデータをフェッチするためだけでなく、更新または削除するテーブル内の行を識別するためにも使用できます。 SQL:2003標準は、そのための位置付け更新および位置付け削除SQLステートメントを定義しています。このようなステートメントは、述部で通常のWHERE句を使用しません。代わりに、カーソルが行を識別します。 FETCHステートメントを使用して、カーソルを開いて行に配置する必要があります。
docs Python sqlite module を確認すると、python module cursor
が必要であることがわかります。 CREATE TABLE
ステートメント。したがって、OPによって正しく指摘されているように、単なるconnection
オブジェクトで十分な場合に使用されます。このような抽象化は、人々がdbカーソルを理解するものとは異なるため、ユーザー側の混乱/欲求不満です。効率に関係なく、それは単なる概念的なオーバーヘッドです。ドキュメントで、python module cursor
がSQLやデータベースのカーソルとは少し異なることが指摘されていればいいでしょう。
結果を取得するにはカーソルオブジェクトが必要です。あなたの例はINSERT
であり、それから行を戻そうとしていないので機能しますが、 sqlite3
docs 、あなたは.fetchXXXX
メソッドは接続オブジェクトにあるため、カーソルなしでSELECT
を実行しようとした場合、結果のデータを取得する方法はありません。
カーソルオブジェクトを使用すると、最初の結果のフェッチが完了する前に複数のクエリを実行することができるため、どの結果セットがどれであるかを追跡できます。
公式によれば docsconnection.execute()
は、中間カーソルオブジェクトを作成する非標準のショートカットです。
Connection.execute
これは、cursor()メソッドを呼び出してカーソルオブジェクトを作成し、指定されたパラメーターでカーソルのexecute()メソッドを呼び出し、カーソルを返す非標準のショートカットです。
12.6.8。 sqlite3efficientlyの使用
12.6.8.1。 shortcutメソッドの使用
Connectionオブジェクトのnonstandard
execute()
、executemany()
およびexecutescript()
メソッドを使用して、コードを記述できますより簡潔になります。これは、(多くの場合superfluous)Cursorオブジェクトを明示的に作成する必要がないためです。代わりに、Cursorオブジェクトが暗黙的に作成され、これらのショートカットメソッドはカーソルオブジェクトを返します。このようにして、SELECTステートメントを実行し、Connectionオブジェクトで1回の呼び出しのみを使用して直接繰り返すことができます。
( sqlite3のドキュメント ;私の強調。)
接続オブジェクトを使用しないのはなぜですか?
接続オブジェクトのメソッドは 非標準 であるため、つまり Python Database API Specification v2. (PEP 249)の一部ではありません。
Cursorオブジェクトの標準メソッドを使用する限り、上記の仕様に従う別のデータベース実装に切り替えた場合、コードは完全に移植可能になります。おそらく、import
行を変更するだけで済みます。
ただし、connection.execute
を使用すると、切り替えがそれほど簡単ではなくなる可能性があります。これが、代わりにcursor.execute
を使用する主な理由です。
ただし、切り替えないことが確実な場合は、connection.execute
ショートカットを使用して "効率的"であっても完全に問題ないと思います。
データベースへの同じ接続を介して、複数の個別の作業環境を使用することができます。