Notatka
Dostęp do tej strony wymaga autoryzacji. Może spróbować zalogować się lub zmienić katalogi.
Dostęp do tej strony wymaga autoryzacji. Możesz spróbować zmienić katalogi.
Sterownik mssql-python oferuje kilka metod pobierania, wzorców dostępu wierszowego oraz funkcje nawigacji kursorem do pobierania wyników zapytań.
Metody pobierania
Po wykonaniu zapytania SELECT użyj metod pobierania do pobrania wyników.
fetchone()
Zwraca pojedynczy wiersz lub None jeśli nie ma już dostępnych wierszy:
cursor.execute("SELECT ProductID, Name, ListPrice FROM Production.Product")
row = cursor.fetchone()
while row:
print(f"{row.ProductID}: {row.Name} - ${row.ListPrice}")
row = cursor.fetchone()
fetchmany()
Zwraca listę wierszy.
cursor.arraysize kontroluje domyślny rozmiar partii (domyślny: 1):
cursor.execute("SELECT * FROM Production.Product")
cursor.arraysize = 100 # Fetch 100 rows at a time
while True:
rows = cursor.fetchmany()
if not rows:
break
for row in rows:
print(row.Name)
Możesz też bezpośrednio określić rozmiar:
rows = cursor.fetchmany(50) # Fetch up to 50 rows
fetchall()
Zwraca wszystkie pozostałe wiersze jako listę:
cursor.execute("SELECT * FROM Production.Product WHERE Color = 'Black'")
rows = cursor.fetchall()
print(f"Found {len(rows)} products")
for row in rows:
print(row.Name)
fetchval()
Zwraca pierwszą kolumnę pierwszego wiersza, co jest przydatne do zapytań skalarnych.
count = cursor.execute("SELECT COUNT(*) FROM Production.Product").fetchval()
print(f"Total products: {count}")
max_price = cursor.execute("SELECT MAX(ListPrice) FROM Production.Product").fetchval()
print(f"Highest price: ${max_price}")
Wzorce dostępu do wierszy
Klasa Row obsługuje wiele wzorców dostępu.
Dostęp do indeksu
Uzyskaj dostęp do kolumn według pozycji (indeksowanej od zera):
cursor.execute("SELECT ProductID, Name, ListPrice FROM Production.Product WHERE ProductID < 5")
row = cursor.fetchone()
product_id = row[0]
name = row[1]
price = row[2]
Dostęp do atrybutów
Dostęp do kolumn według nazwy:
cursor.execute("SELECT ProductID, Name, ListPrice FROM Production.Product WHERE ProductID < 5")
row = cursor.fetchone()
product_id = row.ProductID
name = row.Name
price = row.ListPrice
Nazwy kolumn małymi literami
Włącz globalne użycie małych liter w nazwach atrybutów:
import mssql_python
settings = mssql_python.get_settings()
settings.lowercase = True
cursor.execute("SELECT ProductID, Name FROM Production.Product WHERE ProductID < 5")
row = cursor.fetchone()
print(row.productid, row.name) # Lowercase access
settings.lowercase = False # Restore default
Iteracja
Wiersze wspierają iterację nad wartościami:
cursor.execute("SELECT ProductID, Name, ListPrice FROM Production.Product WHERE ProductID < 5")
row = cursor.fetchone()
for value in row:
print(value)
Iteracja kursora
Iteruj bezpośrednio po kursorze, aby przetwarzać wiersze:
cursor.execute("SELECT * FROM Production.Product")
for row in cursor:
print(row.Name)
Ten wzorzec jest równoważny powtarzaniu się wywoływania fetchone() .
Metadane kolumn
Dostęp do informacji o kolumnie poprzez cursor.description:
cursor.execute("SELECT ProductID, Name, ListPrice FROM Production.Product WHERE ProductID < 5")
for col in cursor.description:
name, type_code, display_size, internal_size, precision, scale, null_ok = col
print(f"Column: {name}, Type: {type_code}, Nullable: {null_ok}")
Liczba wierszy
Atrybut wskazuje cursor.rowcount :
- Dla instrukcji SELECT: Zwraca -1 po
execute()do momentu rozpoczęcia pobierania. Gdy zaczniesz pobierać, pokazuje łączną liczbę dotychczas pobranych wierszy. - Dla INSERT/UPDATE/DELETE: Liczba wierszy dotkniętych zmianą.
cursor.execute("SELECT * FROM Production.Product")
print(f"Rows returned: {cursor.rowcount}")
cursor.execute("CREATE TABLE #PriceUpd (Name NVARCHAR(50), Price DECIMAL(10,2), CategoryID INT)")
cursor.execute("INSERT INTO #PriceUpd VALUES ('A',10,1),('B',20,1),('C',30,2)")
cursor.execute("UPDATE #PriceUpd SET Price = Price * 1.1 WHERE CategoryID = 1")
print(f"Rows updated: {cursor.rowcount}")
Nawigacja kursorem
skip()
Pomiń wiersze bez ich pobierania:
cursor.execute("SELECT * FROM Production.Product ORDER BY ProductID")
cursor.skip(10) # Skip first 10 rows
row = cursor.fetchone() # Returns 11th row
scroll()
Przesuń pozycję kursora do przodu:
cursor.execute("SELECT * FROM Production.Product ORDER BY ProductID")
# Move forward 5 rows from current position
cursor.scroll(5, mode='relative')
row = cursor.fetchone()
Note
Sterownik obsługuje tylko dodatnie wartości mode='relative'. Pozycjonowanie bezwzględne i przewijanie do tyłu powodują wystąpienie NotSupportedError, ponieważ sterownik używa kursorów przewijanych tylko do przodu.
numer wiersza
Śledź aktualną sytuację:
cursor.execute("SELECT * FROM Production.Product")
print(f"Initial position: {cursor.rownumber}") # -1 (before first fetch)
row = cursor.fetchone()
print(f"After fetchone: {cursor.rownumber}") # 0 (first row fetched)
Wiele zestawów wyników
Wykorzystanie nextset() do przetwarzania wielu zbiorów wyników:
cursor.execute("""
SELECT * FROM Production.Product WHERE Color = 'Black';
SELECT * FROM Production.ProductCategory;
SELECT COUNT(*) FROM Production.Product;
""")
# First result set
products = cursor.fetchall()
print(f"Products: {len(products)}")
# Move to second result set
if cursor.nextset():
categories = cursor.fetchall()
print(f"Categories: {len(categories)}")
# Move to third result set
if cursor.nextset():
count = cursor.fetchval()
print(f"Total count: {count}")
Duże zbiory wyników
Dla dużych zbiorów wyników przetwarzamy wiersze w partiach do zarządzania pamięcią:
def process_batch(rows):
# Example: print each row. Replace with your own logic.
for row in rows:
print(row)
cursor.execute("SELECT * FROM LargeTable")
cursor.arraysize = 1000
while True:
rows = cursor.fetchmany()
if not rows:
break
process_batch(rows)
print(f"Processed {cursor.rownumber} rows so far")
Menedżerowie kontekstu
Używaj menedżerów kontekstu do automatycznego czyszczenia zasobów:
with mssql_python.connect(connection_string) as conn:
with conn.cursor() as cursor:
cursor.execute("SELECT * FROM Production.Product")
for row in cursor:
print(row.Name)
# Cursor and connection closed automatically
Najlepsze rozwiązania
-
Używaj
fetchmany()do dużych wyników , aby uniknąć ładowania wszystkiego do pamięci. - Zamykaj kursory, gdy to robisz, aby zwolnić zasoby serwera.
- Używaj nazw kolumn (dostęp do atrybutów), aby kod był bardziej czytelny.
-
Sprawdź
rowcountpo instrukcjach modyfikujących dane. -
Jawnie obsługuj wartości
Nonegdy kolumny mogą przyjmować wartość NULL.