Frage

Warum wird mit '*' Blick schlecht zu bauen?

Angenommen

, dass Sie einen Komplex haben beitreten und alle Felder können irgendwo verwendet werden.

Dann müssen Sie nur noch wählten Felder benötigt.

SELECT field1, field2 FROM aview WHERE ...

In der Ansicht "aview" SELECT table1.*, table2.* ... FROM table1 INNER JOIN table2 ... werden könnte

Wir haben ein Problem, wenn zwei Felder die gleichen Namen in Tabelle 1 und Tabelle 2 haben.

Ist das nur der Grund, warum mit ‚*‘ in einer Ansicht, schlecht ist?

Mit ‚*‘, können Sie die Ansicht in einem anderen Kontext verwenden, da die Informationen dort sind.

Was bin ich fehlt?

Viele Grüße

War es hilfreich?

Lösung

Das glaube ich nicht, dass es viel in Software, die „einfach nur schlecht“, aber es gibt viele Dinge, die in schlechten Möglichkeiten missbraucht wird: -)

Das Beispiel Sie geben, ist ein Grund, warum * Sie vielleicht nicht, was Sie erwarten, und ich denke, es gibt andere. Zum Beispiel, wenn die zugrunde liegenden Tabellen ändern, werden vielleicht Spalten hinzugefügt oder entfernt wird, eine Ansicht, die * verwendet wird weiterhin gültig sein, aber vielleicht alle Anwendungen brechen, die sie verwenden. Wenn Ihre Ansicht explizit die Spalten genannt hatte dann gibt es noch eine Chance, dass jemand würde das Problem erkennen, wenn die Schemaänderung zu machen.

Auf der anderen Seite könnten Sie wirklich wollen Ihre Ansicht ungeniert nehmen alle Änderungen an den zugrunde liegenden Tabellen, in diesem Fall ein * würde genau das, was Sie wollen.

Update: Ich weiß nicht, ob die OP einen bestimmten Datenbankanbieter im Sinne hatten, aber es ist jetzt klar, dass meine letzte Bemerkung nicht zutrifft für alle Arten. Ich verdanke user12861 und Jonny Leeds für den Hinweis, und leider es mehr als 6 Jahre gedauert hat für mich, meine Antwort zu bearbeiten.

Andere Tipps

Obwohl viele der Kommentare hier sind sehr gut und Referenz ein häufiges Problem von Wildcards in Abfragen, wie zB verursacht Fehler oder unterschiedliche Ergebnisse zu verwenden, wenn die zugrunde liegenden Tabellen ändern, ein anderes Thema, das nicht abgedeckt wurde, ist die Optimierung. Eine Abfrage, die jede Spalte einer Tabelle zieht neigt nicht ganz so effizient wie eine Abfrage, die Sie tatsächlich benötigen nur die Spalten zieht. Zugegeben, es gibt jene Zeiten, in denen Sie jede Spalte brauchen, und es ist ein wichtiges PIA sie alle, vor allem in einer großen Tabelle zu verweisen ist, aber wenn Sie nur eine Teilmenge benötigen, warum Ihre Abfrage mit mehreren Spalten biegen nach unten, als Sie benötigen.

Ein weiterer Grund, warum „*“ riskant ist, nicht nur in Aussicht, aber in Abfragen ist, dass Spalte Namen oder Position in den zugrundeliegenden Tabellen ändern ändern können. eine Wildcard bedeutet, dass Ihre Ansicht geändert werden, ohne dass solche Änderungen leicht aufnimmt. Aber wenn Ihre Anwendung Referenzen Spalten von Position in der Ergebnismenge, oder wenn Sie eine dynamische Sprache verwenden, die Ergebnismengen von Spaltennamen eingegeben gibt, könnten Sie Probleme auftreten, die zu debuggen hart sind.

Ich vermeide das Wildcard jederzeit verwenden. Auf diese Weise, wenn ein Spaltennamen ändert, erhalte ich einen Fehler in der Ansicht oder Abfrage sofort, und ich weiß, wo es zu beheben. Wenn eine Spalte Position in der zugrunde liegenden Tabelle ändert, die Reihenfolge der Spalten in der Ansicht Angabe oder Abfrage kompensiert dies.

Diese anderen Antworten haben alle gute Punkte, aber auf SQL-Server zumindest haben sie auch einige falsche Punkte. Versuchen Sie folgendes:

create table temp (i int, j int)
go
create view vtemp as select * from temp
go
insert temp select 1, 1
go
alter table temp add k int
go
insert temp select 1, 1, 1
go
select * from vtemp

SQL Server nicht lernen, über die „neue“ Spalte, wenn es hinzugefügt wird. Je nachdem, was Sie dies wünschen könnte eine gute Sache oder eine schlechte Sache sein, aber so oder so, es ist wahrscheinlich nicht gut auf sie angewiesen. So ist es zu vermeiden scheint wie eine gute Idee.

Für mich ist dieses seltsame Verhalten ist der überzeugendste Grund select * in Ansichten zu vermeiden.

Die Kommentare haben mich gelehrt, dass MySQL ähnliches Verhalten hat und Oracle nicht (es wird über Änderungen an der Tabelle lernen). Diese Inkonsistenz ich ist umso mehr Grund, nicht select * in Ansichten zu verwenden.

Mit ‚*‘ für alles, was die Produktion schlecht ist. Es ist toll für einmalige Anfragen, aber im Produktionscode sollten Sie immer so explizit wie möglich sein.

Für Ansichten insbesondere dann, wenn die zugrunde liegenden Tabellen Spalten hinzugefügt oder entfernt werden, entweder die Ansicht falsch sein oder gebrochen, bis sie neu kompiliert wird.

Mit SELECT * innerhalb der Ansicht nicht viel von einer Performance-Overhead nicht entstehen, wenn Spalten nicht außerhalb der Ansicht verwendet werden - das Optimierungsprogramm wird sie optimieren heraus; SELECT * FROM TheView kann vielleicht Abfall Bandbreite, genau wie jedes Mal, wenn Sie mehr Spalten in einem Netzwerk ziehen.

In der Tat habe ich festgestellt, dass die Ansichten, die verbinden fast alle Spalten aus einer Reihe von großen Tabellen in meiner Data-Warehouse keine Performance-Probleme überhaupt eingeführt haben, auch durch relativ wenige dieser Spalten von außerhalb der Ansicht angefordert werden. Die Optimierer Griff, die gut und ist in der Lage sehr gut zu den externen Filterkriterien nach unten in den Blick drücken.

Doch für alle oben genannten Gründen, benutze ich nur sehr selten SELECT *.

Ich habe einige Business-Prozesse, bei denen eine Reihe von CTEs auf der jeweils anderen gebaut werden, effektiv abgeleitet Spalten von abgeleiteten Spalten von abgeleiteten Spalten Gebäude (die hoffentlich eines Tages, als das Geschäft Refactoring wird rationalisiert und vereinfacht diese Berechnungen), und in diesem Fall muß ich alle Spalten durch jedes Mal fallen zu lassen, und ich verwende SELECT * -. aber SELECT * nicht an der Basisschicht verwendet wird, nur zwischen dem ersten CTE und die letzten

Die Lage auf SQL Server ist eigentlich noch schlimmer als die Antwort von @ user12861 bedeutet: Wenn Sie SELECT * gegen mehrere Tabellen verwenden, Hinzufügen von Spalten zu einer Tabelle in der Abfrage verwies früh tatsächlich dazu führen, dass Ansicht, die die Werte des neuen zurückzukehren Spalten unter dem Deckmantel der alten Säulen. Siehe nachstehendes Beispiel:

-- create two tables
CREATE TABLE temp1 (ColumnA INT, ColumnB DATE, ColumnC DECIMAL(2,1))
CREATE TABLE temp2 (ColumnX INT, ColumnY DATE, ColumnZ DECIMAL(2,1))
GO


-- populate with dummy data
INSERT INTO temp1 (ColumnA, ColumnB, ColumnC) VALUES (1, '1/1/1900', 0.5)
INSERT INTO temp2 (ColumnX, ColumnY, ColumnZ) VALUES (1, '1/1/1900', 0.5)
GO


-- create a view with a pair of SELECT * statements
CREATE VIEW vwtemp AS 
SELECT *
FROM temp1 INNER JOIN temp2 ON 1=1
GO


-- SELECT showing the columns properly assigned
SELECT * FROM vwTemp 
GO


-- add a few columns to the first table referenced in the SELECT 
ALTER TABLE temp1 ADD ColumnD varchar(1)
ALTER TABLE temp1 ADD ColumnE varchar(1)
ALTER TABLE temp1 ADD ColumnF varchar(1)
GO


-- populate those columns with dummy data
UPDATE temp1 SET ColumnD = 'D', ColumnE = 'E', ColumnF = 'F'
GO


-- notice that the original columns have the wrong data in them now, causing any datatype-specific queries (e.g., arithmetic, dateadd, etc.) to fail
SELECT *
FROM vwtemp
GO

-- clean up
DROP VIEW vwTemp
DROP TABLE temp2
DROP TABLE temp1

Es ist, weil Sie nicht immer jede Variable benötigen, und auch sicherstellen, dass Sie darüber nachdenken, was Sie speziell benötigen.

Es gibt keinen Punkt, all Hash-Passwörter aus der Datenbank, wenn eine Liste von Benutzern auf Ihrer Website zum Beispiel Gebäude, so dass ein select * unproduktiv sein würde.

Es ist einmal, habe ich eine Ansicht für eine Tabelle in einer anderen Datenbank (auf demselben Server) mit

Select * From dbname..tablename

Dann, einen Tag wurde eine Spalte zu der anvisierten Tabelle hinzugefügt. Die Ansicht begann völlig falsche Ergebnisse zurückkehrt, bis sie umgeschichtet wurde.


Völlig falsch. Keine Zeilen

Dies war auf SQL Server 2000.

ich spekulieren, dass dies wegen der syscolumns Werte ist, dass die Ansicht gewonnen hatte, auch wenn ich gebraucht *.

Eine SQL-Abfrage ist im Grunde eine Funktionseinheit von einem Programmierer für die Verwendung in einem bestimmten Kontext. Für die langfristige Stabilität und Wartbarkeit (möglicherweise durch eine andere Person als Sie) alles in einer Funktionseinheit für einen bestimmten Zweck sein sollte, und es sollte ziemlich offensichtlich (oder dokumentiert), warum es sie gibt -. Insbesondere jedes Element von Daten

Wenn ich ab jetzt mit dem Bedarf oder Wunsch auf zwei Jahre kommen war Ihre Abfrage zu ändern, würde ich erwarten, dass es grok ziemlich gründlich, bevor ich sicher sein würde, dass ich konnte mit ihrem Durcheinander. Was bedeutet, ich würde müssen verstehen, warum alle Spalten aus aufgerufen werden. (Dies ist umso offensichtlich wahr, wenn Sie versuchen, die Abfrage in mehr als ein Kontext wieder zu verwenden. Welche problematisch ist im Allgemeinen, aus ähnlichen Gründen.) Wenn ich Spalten in der Ausgabe sehen, dass ich nicht zu einem bestimmten Zweck in Zusammenhang stehen könnte , würde ich ziemlich sicher sein, dass ich nicht verstand, was es getan hat, und warum, und was die Folgen wären es zu ändern.

Es ist generell eine schlechte Idee * zu verwenden. Einige Code-Zertifizierung Motoren markieren dies als Warnung und beraten Sie explizit nur die erforderlichen Spalten beziehen. Die Verwendung von * kann, um die Leistung führen louses, da Sie nur einige Spalten benötigen könnten und nicht alle. Aber auf der anderen Seite gibt es einige Fälle, in denen die Verwendung von * ideal ist. Stellen Sie sich vor, dass, egal was passiert, am Beispiel Ihnen zur Verfügung gestellten, für diese Ansicht (aview) Sie immer alle Spalten in diesen Tabellen benötigen würde. In Zukunft, wenn eine Spalte hinzugefügt wird, würden Sie nicht brauchen, um die Ansicht zu ändern. Das kann gut oder schlecht sein, je den Fall, dass Sie es zu tun haben.

Ich denke, es hängt von der Sprache Sie verwenden. Ich bevor select * verwenden, wenn die Sprache oder DB Fahrer ein dict zurückgibt (Python, Perl, etc.) oder assoziative Array (PHP) der Ergebnisse. Es macht Ihren Code viel leichter zu verstehen, wenn man mit dem Namen der Spalte beziehen, anstatt als Index in einem Array.

Niemand sonst scheint es erwähnt zu haben, aber innerhalb von SQL Server können Sie auch Ihre Ansicht mit der SCHEMAB Attribut.

Dies verhindert, dass Änderungen an einem der Basistabellen (einschließlich Drop), die die Sichtdefinition beeinflussen würde.

Dies kann für einige Situationen für Sie nützlich. Ich weiß, dass ich nicht genau Ihre Frage beantwortet, aber ich dachte, es dennoch hervorheben würde.

Und wenn Sie Joins wählen Sie mit * automatisch bedeutet, dass Sie mehr Daten zurückkommen, als Sie benötigen, da die Daten in den Join-Felder wiederholt. Dies ist eine Verschwendung von Datenbank- und Netzwerkressourcen.

Wenn Sie naiv genug sind Ansichten zu verwenden, die andere Ansichten aufrufen, wählen Sie * verwenden, können sie noch schlimmer Performer machen (Dies ist Technik, die für die Leistung auf seine eigene schlecht ist, ruft mulitple Spalten, die Sie nicht brauchen, macht es viel schlimmer ).

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top