Ich möchte hier keinen Religionskrieg auslösen, aber es scheint zwei Denkschulen zu geben, wie man boolesche Werte in einer Datenbank darstellt. Einige sagen, es bit
sei der geeignete Datentyp, während andere argumentieren, es tinyint
sei besser.
Die einzigen Unterschiede, die mir bekannt sind, sind folgende:
bit
: Speichergröße ist 1 Bit, mögliche Werte sind 0 oder 1tinyint
: Speichergröße ist 1 Byte, mögliche Werte sind 0-255
Welcher Datentyp ist besser, wenn Sie boolesche Werte darstellen müssen? Lohnt sich tinyint
der zusätzliche Aufwand "nur für den Fall", dass Sie Werte> 1 benötigen?
sql
mysql
sql-server
types
Seibar
quelle
quelle
Antworten:
Wenn Sie Ihrer Tabelle eine Bitspalte hinzufügen, belegt diese in jedem Datensatz ein ganzes Byte und nicht nur ein einzelnes Bit. Wenn Sie eine zweite Bitspalte hinzufügen, wird diese im selben Byte gespeichert. Die neunte Bitspalte benötigt ein zweites Byte Speicher. Tabellen mit 1-Bit-Spalte erhalten keinen Speichervorteil.
Tinyint und Bit können beide zum Arbeiten gebracht werden, ich habe beide erfolgreich verwendet und habe keine starke Präferenz.
quelle
Bit ... es sei denn, Sie gehören dem Clan "true / false / file not found" an
Falls Sie die Referenz nicht erhalten haben ...
Und im Fall von Linq2SQL arbeitet Bit mit true / false, was die Programmierung erleichtert. Beides hat Vorteile.
Außerdem muss die Programmierwartung berücksichtigt werden. Was passiert, wenn Sie (oder ein Junior-Praktikant) 2, 3, 25, 41, 167, 200 usw. verwenden? Wo ist das dokumentiert? Bits sind selbstdokumentierend und ziemlich universell.
quelle
Ich benutze Bits, wenn es angebracht ist. Abgesehen davon, dass es semantisch der richtige Typ ist (Anzahl der Semantiken!), Können mehrere Bitfelder (bis zu 8) in einer einzelnen Zeile (jedenfalls unter SQL Server) in einem einzigen Speicherbyte konsolidiert werden. Nach dem achten wird ein zusätzliches Byte für die nächsten 8 benötigt und so weiter.
Verweise:
quelle
Für MySQL-Benutzer - Warum Sie in MySQL keine BIT-Spalten verwenden sollten
quelle
Ein früherer StackOverflow-Beitrag: Was ist der Unterschied zwischen BIT und TINYINT in MySQL?
Beim Hinzufügen einer neuen "BOOL" -Spalte verwendet MySQL tatsächlich TINYINT.
Ich würde einfach bei BOOL (auch bekannt als TINYINT ) bleiben und mit dem Leben weitermachen .
quelle
Boolean erlaubt per Definition nur zwei Werte. Warum brauchen Sie dafür mehr als ein einziges Bit? Wenn Sie eine Logik mit drei (oder mehr) Zuständen benötigen, verwenden Sie einen größeren Datentyp, aber ich würde (und würde) bei Bitfeldern für die Standard-Boolesche Logik bleiben.
quelle
Ich verwende Bit, weil ich dadurch keine Prüfbedingung verwenden muss und weil mein ORM das Bit automatisch in einen nullbaren Booleschen Wert (C #) konvertiert, was ich nach dem Codieren sehr schätze.
quelle
Null Platz für Falsch
Unabhängig von Ihrer Wahl können Sie
NULL
stattdessen festlegen,0
dass kein zusätzlicher Speicherplatz belegt wird (da die Datenbank fast immer einNULL
Flag für jedes Feld jeder Zeile enthält, das nur dort sitzt; weitere Informationen hier ). Wenn Sie auch sicherstellen, dass der Standardwert / wahrscheinlichste Wert istfalse
, sparen Sie noch mehr Platz!Etwas Platz für Wahr
Der darzustellende Wert
true
erfordert den durch den Feldtyp definierten Platz. Mit usingBIT
wird nur dann Platz gespart, wenn eine Tabelle mehrere solcher Spalten enthält, da ein Byte pro 8 Felder verwendet wird (gegenüberTINYINT
einem Byte pro Feld).TINYINT
bietet den Vorteil, dass Sie eine Bitmaske mit 8 Werten anpassen können, ohne sich um die Verwaltung einer Reihe zusätzlicher Spalten kümmern zu müssen, und die Suche ist theoretisch schneller (ein einzelnes ganzzahliges Feld im Vergleich zu mehreren Bitfeldern). Es gibt jedoch einige Nachteile, wie z. B. eine langsamere Reihenfolge, ausgefallene Cross-Indexing-Funktionen und das Fehlen von Feldnamen. Was für mich der größte Verlust ist; Ihre Datenbank würde eine externe Dokumentation erfordern, um festzustellen, welche Bits was in welchen Bitmasken getan haben.Vermeiden Sie auf jeden Fall die Versuchung,
TEXT
Felder zum Speichern von Booleschen Werten oder Mengen davon zu verwenden. Das Durchsuchen von Text ist für den Server viel aufwändiger, und beliebige Benennungsschemata wie "Ein, Aus, Aus" können die Interoperabilität beeinträchtigen.quelle
Ich habe gerade versucht, auf Bit (SQL Server 2k5) zu gruppieren, und es hat bei mir gut funktioniert. Ich verwende gerne den richtigen Datentyp für die Anwendung. Wenn es ein wahres / falsches Feld ist, dann ist Bit das, was ich benutze ...
quelle
All diese theoretischen Diskussionen sind großartig, aber in der Realität ist es, zumindest wenn Sie MySQL und wirklich auch für SQLServer verwenden, am besten, nicht-binäre Daten für Ihre Booleschen Werte beizubehalten, aus dem einfachen Grund, dass es einfacher ist, mit ihnen zu arbeiten geben die Daten aus, fragen ab und so weiter. Dies ist besonders wichtig, wenn Sie versuchen, eine Interoperabilität zwischen MySQL und SQLServer zu erreichen (dh Sie synchronisieren Daten zwischen beiden), da die Behandlung des BIT-Datentyps in beiden Fällen unterschiedlich ist. In der Praxis werden Sie also viel weniger Probleme haben, wenn Sie sich an einen numerischen Datentyp halten. Ich würde MySQL empfehlen, bei BOOL oder BOOLEAN zu bleiben, die als TINYINT (1) gespeichert werden. Selbst die Art und Weise, wie MySQL Workbench und MySQL Administrator den BIT-Datentyp anzeigen, ist nicht gut (es ist ein kleines Symbol für Binärdaten).
quelle
Ich glaube nicht, dass ich es oben erwähnt habe, aber es gibt das Problem, dass BIT-Spalten (z. B. MIN, MAX und insbesondere SUM) nicht aggregiert werden können. Ich habe gerade mit 2008 getestet und das Problem ist immer noch da. Das ist der Hauptgrund, warum ich in letzter Zeit tinyint verwende - das andere ist, dass ich mag, wie tinyint skaliert - es ist immer ein Schmerz, wenn Ihr "Zwei-Wert" -Bit-Flag plötzlich mehr mögliche Werte benötigt.
quelle
Wir erstellen alle unsere Tabellen mit einem int "Vektor" -Feld. Wir verwenden dieses Feld dann als Sammlung von 32 Bits, die wir für jeden Zweck zuweisen können. (Möglicherweise wird eine Gruppe von Bits für eine Reihe von Zuständen verwendet). Vermeidet, dass wir ständig Flaggenfelder hinzufügen müssen, wenn wir dies vergessen.
quelle
@ Kevin: Ich glaube, Sie können
group by
auf Bitfeldern verwenden (SQL Server 2005):declare @t table ( descr varchar(10), myBit1 bit, myBit2 bit ) insert into @t values ('test1', 0, 1) insert into @t values ('test2', 1, 0) insert into @t values ('test3', 1, 1) insert into @t values ('test4', 0, 0) select myBit1, count(myBit1) from @t group by myBit1 select myBit2, count(myBit1) from @t group by myBit2
Ergebnisse:
myBit1 ------ ----------- 0 2 1 2 myBit2 ------ ----------- 0 2 1 2
quelle
TinyInt ist meine Präferenz. Wenn Sie dann aggregierte Zählungen für das Feld durchführen, müssen Sie es nicht wirken. Außerdem interpretieren einige Front-End-Sprachen ein Bit anders als andere, und die Verwendung eines TinyInt macht Validierungsprüfungen für jede Front-End-Sprache universell.
quelle
Wenn Sie MySQL verwenden, wird die Verwendung des BIT-Datentyps nicht empfohlen - http://www.xaprb.com/blog/2006/04/11/bit-values-in-mysql/
quelle
Ich benutze gerne char (1) mit 'T' oder 'F'. Ja, es kann mit anderen Werten missbraucht werden, aber zumindest ist es einfach, es in Berichten oder an anderen Stellen anzuzeigen, an denen es schwieriger ist, mit Bit- oder Binärwerten zu arbeiten.
quelle
-1
, um wahr und0
falsch darzustellen.