it-swarm.com.de

MySQL: Große VARCHAR vs. TEXT?

Ich habe eine Nachrichtentabelle in MySQL, die Nachrichten zwischen Benutzern aufzeichnet. Abgesehen von den typischen IDs und Nachrichtentypen (alle Integer-Typen) muss der eigentliche Nachrichtentext entweder als VARCHAR oder TEXT gespeichert werden. Ich setze ein Front-End-Limit von 3000 Zeichen, was bedeutet, dass die Nachrichten niemals so lange in die Datenbank eingefügt werden.

Gibt es einen Grund dafür, entweder mit VARCHAR (3000) oder mit TEXT zu arbeiten? Es hat etwas mit dem Schreiben von VARCHAR (3000) zu tun, das sich nicht intuitiv anfühlt. Ich habe andere ähnliche Posts über Stack Overflow durchgesehen, wäre aber gut, wenn ich mir spezielle Ansichten für diese Art des gemeinsamen Speicherns von Nachrichten holen würde.

818
Tom
  • TEXT und BLOB werden außerhalb der Tabelle gespeichert, wobei die Tabelle nur einen Zeiger auf den Ort des tatsächlichen Speichers enthält.

  • VARCHAR wird inline mit der Tabelle gespeichert. VARCHAR ist schneller, wenn die Größe angemessen ist. Der Kompromiss hängt von Ihren Daten und Ihrer Hardware ab. Sie möchten ein reales Szenario mit Ihren Daten vergleichen.

pdate Ob VARCHAR oder TEXT inline oder offline gespeichert wird, hängt von der Datengröße, der Spaltengröße, dem Zeilenformat und der MySQL-Version ab. Es hängt nicht von "text" vs "varchar" ab.

792
MindStalker

Können Sie vorhersagen, wie lange die Benutzereingabe dauern würde?

VARCHAR (X)

Fall: Benutzername, E-Mail, Land, Betreff, Passwort


TEXT

Fall: Nachrichten, E-Mails, Kommentare, formatierter Text, HTML, Code, Bilder, Links


MEDIUMTEXT

case: große json body, kurze bis mittellange bücher, csv strings


LONGTEXT

Case: Lehrbücher, Programme, jahrelange Protokolldateien, Harry Potter und der Feuerkelch, Protokollierung wissenschaftlicher Untersuchungen

450

Nur um die Best Practice zu verdeutlichen:

  1. Textnachrichten sollten fast immer als TEXT gespeichert werden (sie sind am Ende beliebig lang)

  2. Zeichenfolgenattribute sollten als VARCHAR gespeichert werden (der Zielbenutzername, der Betreff usw.).

Ich verstehe, dass Sie ein Front-End-Limit haben, das großartig ist, bis es nicht mehr ist. * grins * Der Trick besteht darin, sich die Datenbank getrennt von den Anwendungen vorzustellen, die eine Verbindung zu ihr herstellen. Nur weil eine Anwendung die Daten begrenzt, bedeutet dies nicht, dass die Daten in sich begrenzt sind.

Was ist mit den Nachrichten selbst, das sie zwingt, nie mehr als 3000 Zeichen zu sein? Wenn es sich nur um eine beliebige Anwendungseinschränkung handelt (z. B. für ein Textfeld oder ähnliches), verwenden Sie ein TEXT -Feld auf der Datenebene.

216
James

Haftungsausschluss: Ich bin kein MySQL-Experte ... aber dies ist mein Verständnis der Probleme.

Ich denke, TEXT wird außerhalb der MySQL-Zeile gespeichert, während VARCHAR als Teil der Zeile gespeichert wird. Es gibt eine maximale Zeilenlänge für MySQL-Zeilen. Sie können also mithilfe von VARCHAR festlegen, wie viele andere Daten in einer Zeile gespeichert werden sollen.

Auch aufgrund von VARCHAR, das Teil der Zeile ist, vermute ich, dass Abfragen, die dieses Feld betrachten, etwas schneller sind als Abfragen, die einen TEXT-Block verwenden.

32

Kurze Antwort: Kein praktischer Unterschied in Bezug auf Leistung oder Lagerung.

Lange Antwort:

Es gibt im Wesentlichen keinen Unterschied (in MySQL) zwischen VARCHAR(3000) (oder einem anderen großen Limit) und TEXT. Ersteres wird bei 3000 Zeichen abgeschnitten; Letzteres wird bei 65535 Bytes abgeschnitten. (Ich unterscheide zwischen Bytes und Zeichen , da ein Zeichen mehrere Bytes haben kann.)

Für kleinere Grenzen in VARCHAR gibt es einige Vorteile gegenüber TEXT.

  • "kleiner" bedeutet 191, 255, 512, 767 oder 3072 usw., je nach Version, Kontext und CHARACTER SET.
  • INDEXes gibt an, wie groß eine Spalte indiziert werden kann. (767 oder 3072 Bytes ; dies ist versions- und einstellungsabhängig)
  • Durch complex SELECTs erstellte Zwischentabellen werden auf zwei verschiedene Arten behandelt - MEMORY (schneller) oder MyISAM (langsamer). Wenn 'große' Spalten betroffen sind, wird die langsamere Technik automatisch ausgewählt. (Wichtige Änderungen in Version 8.0; Änderungen an diesem Aufzählungszeichen vorbehalten.)
  • In Bezug auf das vorherige Element springen alle TEXT -Datentypen (im Gegensatz zu VARCHAR) direkt zu MyISAM. Das heißt, TINYTEXT ist für generierte temporäre Tabellen automatisch schlechter als das entsprechende VARCHAR. (Aber das bringt die Diskussion in eine dritte Richtung!)
  • VARBINARY ist wie VARCHAR; BLOB ist wie TEXT.

Widerlegung auf andere Antworten

Bei der ursprünglichen Frage wurde eine Frage gestellt (welcher Datentyp verwendet werden soll). Die akzeptierte Antwort beantwortete etwas anderes (Off-Record-Speicherung). Diese Antwort ist jetzt nicht mehr aktuell.

Als dieser Thread gestartet und beantwortet wurde, gab es in InnoDB nur zwei "Zeilenformate". Bald darauf wurden zwei weitere Formate (DYNAMIC und COMPRESSES) eingeführt.

Der Speicherort für TEXT und VARCHAR() basiert auf Größe , nicht auf Name des Datentyps . Eine aktualisierte Diskussion über das Speichern von großen Text-/Blob-Spalten auf/außerhalb des Datensatzes finden Sie unter this .

23
Rick James

Die vorangegangenen Antworten bestehen nicht genug auf dem Hauptproblem: Selbst bei sehr einfachen Fragen wie

(SELECT t2.* FROM t1, t2 WHERE t2.id = t1.id ORDER BY t1.id) 

eine temporäre Tabelle kann erforderlich sein. Wenn ein VARCHAR -Feld beteiligt ist, wird es in ein CHAR -Feld in der temporären Tabelle konvertiert. Wenn Sie also in Ihrer Tabelle 500 000 Zeilen mit einem VARCHAR(65000) -Feld haben, verwendet nur diese Spalte 6.5 * 5 * 10 ^ 9 Byte. Solche temporären Tabellen können nicht im Arbeitsspeicher verwaltet werden und werden auf die Festplatte geschrieben. Es ist zu erwarten, dass die Auswirkungen katastrophal sind.

Quelle (mit Metriken): https://nicj.net/mysql-text-vs-varchar-performance/ (Dies bezieht sich auf die Behandlung von TEXT vs VARCHAR in "Standard" (?) MyISAM-Speicher-Engine, bei anderen, z. B. InnoDB, möglicherweise anders.)

7
Max

Varchar steht für kleine Daten wie E-Mail-Adressen, während Text für viel größere Daten wie Nachrichtenartikel und Blob für binäre Daten wie Bilder steht.

Die Leistung von Varchar ist leistungsfähiger, da es vollständig aus dem Speicher ausgeführt wird. Dies ist jedoch nicht der Fall, wenn die Datenmenge zu groß ist, beispielsweise varchar(4000).

Text hingegen bleibt nicht im Speicher und wird von der Festplattenleistung beeinflusst. Sie können dies jedoch vermeiden, indem Sie Textdaten in einer separaten Tabelle trennen und eine Left-Join-Abfrage anwenden, um Textdaten abzurufen.

Blob ist viel langsamer, verwenden Sie es also nur, wenn Sie nicht viele Daten wie 10000 Bilder haben, die 10000 Datensätze kosten.

Befolgen Sie diese Tipps für maximale Geschwindigkeit und Leistung:

  1. Verwenden Sie varchar für Namen, Titel und E-Mails

  2. Verwenden Sie Text für große Datenmengen

  3. Separater Text in verschiedenen Tabellen

  4. Verwenden Sie Left Join-Abfragen für eine ID wie z. B. eine Telefonnummer

  5. Wenn Sie Blob verwenden möchten, wenden Sie die gleichen Tipps wie in Text an

Dadurch kosten Abfragen bei Tabellen mit Daten> 10 MB und einer garantierten Größe von bis zu 10 GB Millisekunden.

2
Creative87

Es gibt einen GROSSEN Unterschied zwischen VARCHAR und TEXT. VARCHAR-Felder können indiziert werden, TEXT-Felder nicht. Felder vom Typ VARCHAR werden inline gespeichert, während TEXT offline gespeichert wird. In den Datensätzen werden nur Zeiger auf TEXT-Daten gespeichert.

Wenn Sie Ihr Feld für eine schnellere Suche, Aktualisierung oder Löschung indizieren müssen, als für VARCHAR, egal wie groß. Ein VARCHAR (10000000) ist niemals dasselbe wie ein TEXT-Feld, da diese beiden Datentypen unterschiedlicher Natur sind.

  • Wenn Sie dieses Feld nur zur Archivierung verwenden
  • sie interessieren sich nicht für Datengeschwindigkeitsabruf
  • sie legen Wert auf Geschwindigkeit, verwenden jedoch den Operator '% LIKE%' in Ihrer Suchanfrage, sodass die Indizierung nicht viel hilft
  • sie können keine Begrenzung der Datenlänge vorhersagen

als für TEXT gehen.

0
Viktor Joras