2009-12-08 3 views
8

Wenn ich eine TabelleIndex mit mehreren Spalten - ok, wenn Abfrage nur in einer Spalte durchgeführt wird?

create table sv (id integer, data text) 

und einen Index:

create index myindex_idx on sv (id,text) 

wäre dies immer noch sehr nützlich sein, wenn ich eine Abfrage

tat
select * from sv where id = 10 

Mein Grund für die Nachfrage ist, dass i‘ Ich blicke durch eine Reihe von Tabellen ohne Indizes und sehe verschiedene Kombinationen von Auswahlabfragen. Einige verwendet nur eine Spalte, andere mehr als eins. Muss ich Indizes für beide Sets haben oder ist ein All-inclusive-Index in Ordnung? Ich füge die Indizes für schnellere Suchvorgänge als vollständige Tabellensuchen hinzu.

Beispiel (auf der Grundlage der Antwort von Matt Huggins):

select * from table where col1 = 10 
select * from table where col1 = 10 and col2=12 
select * from table where col1 = 10 and col2=12 and col3 = 16 

alle von Indextabelle abgedeckt werden könnte (co1l1, col2, col3) aber

select * from table where col2=12 

würde einen anderen Index benötigen?

+0

Ich nur <3 StackOverflow. Ausgezeichnete Antworten viel besser als erwartet. Ich akzeptierte die Antwort, die ich verwendet habe, und erlaube der höchsten gewählten Antwort die Ergänzung direkt unter der akzeptierten Antwort – svrist

Antwort

15

Es sollte nützlich sein, da ein Index auf (ID, Text) zuerst indiziert nach ID, dann Text bzw..

  • Wenn Sie nach ID abfragen, wird dieser Index verwendet.
  • Wenn Sie nach ID & Text abfragen, wird dieser Index verwendet.
  • Wenn Sie per Text abfragen, wird dieser Index NICHT verwendet.

Edit: wenn ich sage, es ist „nützlich“, ich meine es im Hinblick auf die Abfragegeschwindigkeit/Optimierung nützlich ist. Wie Sune Rievers darauf hingewiesen hat, bedeutet dies nicht, dass Sie einen eindeutigen Datensatz mit nur einer ID erhalten (es sei denn, Sie geben die ID in Ihrer Tabellendefinition als eindeutig an).

+2

Nun, es könnte verwendet werden, wenn Sie nach 'Text' abfragen - die Kostenschätzung könnte immer noch einen Index-Skip-Scan, Index-Scan oder schnellen vollständigen Index-Scan bevorzugen. –

2

Ich nehme an, id ist Primärschlüssel. Es macht keinen Sinn, dem Index einen Primärschlüssel hinzuzufügen, da dieser immer eindeutig ist. Das Hinzufügen von etwas Einzigartigem zu etwas anderem wird auch einzigartig sein.

Fügen Sie text einen eindeutigen Index hinzu, wenn Sie es wirklich brauchen, andernfalls verwenden Sie einfach id ist Eindeutigkeit für die Tabelle.

Wenn id nicht Ihr Primärschlüssel ist, können Sie kein eindeutiges Ergebnis aus Ihrer Abfrage erhalten.

In Bezug auf Ihr letztes Beispiel mit Lookup auf col2, ich denke, Sie könnten einen anderen Index benötigen. Indizes sind keine Allheilungslösung für Performance-Probleme, manchmal muss Ihr Datenbankentwurf oder Ihre Abfragen optimiert werden, zum Beispiel in gespeicherte Prozeduren umgeschrieben werden (während ich nicht ganz sicher bin, ob Oracle sie hat, bin ich sicher, dass es ein Oracle gibt gleichwertig).

+1

Das Hinzufügen einer weiteren Spalte zu einem PK-Index könnte von Wert sein, wenn es eine erhebliche Anzahl von Abfragen erlaubt, nur den Index zu verwenden und zu vermeiden Tabellenzugriff vollständig. –

+0

Wahr, aber das wäre auch der Fall, wenn der anderen Spalte (Kardinalschlüssel) ein Index hinzugefügt wird. Es kann einen kleinen Leistungszuwachs im zusammengesetzten Schlüssel gegenüber dem Einzelwertschlüssel + einem anderen Index geben. –

8

Oracle unterstützt eine Reihe von Möglichkeiten, einen Index verwenden, und Sie sollten durch das Verständnis alle von ihnen so eine schnelle lesen hier starten: http://download.oracle.com/docs/cd/B19306_01/server.102/b14211/optimops.htm#sthref973

Ihre Anfrage select * from table where col2=12 könnte sinnvollerweise nutzen, um einen Index überspringen Scan, wenn der führende Spalte ist von sehr niedriger Kardinalität, oder ein schneller vollständiger Indexscan, wenn es nicht ist. Dies würde wahrscheinlich für die Ausführung von Berichten ausreichen, für eine OLTP-Abfrage ist es jedoch wahrscheinlich besser, einen Index mit col2 als führende Spalte zu erstellen.

+1

+1 Für die Erwähnung des Index überspringen Scan. Die Indexkomprimierung, die Datenkardinalität und die Statistiken spielen alle zusammen, um den zu verwendenden Plan zu definieren. – ewernli

2

Wenn der Treiber hinter Ihrer Frage ist, dass Sie eine Tabelle mit mehreren Spalten haben und eine beliebige Kombination dieser Spalten in einer Abfrage verwendet werden kann, sollten Sie sich BITMAP-Indizes ansehen.

bei Ihrem Beispiel der Suche:

select * from mytable where col1 = 10 and col2=12 and col3 = 16 

Sie 3 Bitmap-Indizes erstellen können:

create bitmap index ix_mytable_col1 on mytable(col1); 
create bitmap index ix_mytable_col2 on mytable(col2); 
create bitmap index ix_mytable_col3 on mytable(col3); 

Diese Bitmap-Indizes haben den großen Vorteil, dass sie kombiniert werden können nach Bedarf.

So kann jeder der folgenden Abfragen würden eine oder mehrere der Indizes verwenden:

select * from mytable where col1 = 10; 

select * from mytable where col2 = 10 and col3 = 16; 

select * from mytable where col3 = 16; 

So Bitmap-Indizes können für Sie eine Option sein. David Aldridge hat jedoch darauf hingewiesen, dass je nach Datensatz ein einzelner Index (col1, col2, col3) vorzuziehen sein könnte. Wie immer, es kommt darauf an. Sehen Sie sich Ihre Daten an, die wahrscheinlichsten Abfragen für diese Daten, und stellen Sie sicher, dass Ihre Statistiken aktuell sind.

Hoffe, das hilft.

+0

+1 Sehr interessant. Wusste Bitmap-Arrays nicht, aber http://en.wikipedia.org/wiki/Bitmap_index hat einen schönen kurzen Artikel über sie. –

+1

Vorsicht - Bitmap-Indizes sind nicht so gut für die gleichzeitige Änderung geeignet, daher sind sie in OLTP-Systemen normalerweise eine schlechte Wahl. –

+0

Wahr. Schlecht in OLTP - fantastisch in Data Warehouses. "Wie immer, es kommt darauf an". –

Verwandte Themen