Pertanyaan MySQL: VARCHAR Besar vs. TEXT?


Saya punya tabel pesan di MySQL yang mencatat pesan antar pengguna. Selain tipe id dan pesan tipikal (semua tipe integer) saya perlu menyimpan teks pesan yang sebenarnya sebagai VARCHAR atau TEXT. Saya menetapkan batas front-end dari 3000 karakter yang berarti pesan tidak akan pernah dimasukkan ke dalam db lebih lama dari ini.

Apakah ada alasan untuk pergi dengan VARCHAR (3000) atau TEXT? Ada sesuatu tentang menulis VARCHAR (3000) yang terasa agak kontra-intuitif. Saya telah melalui posting serupa lainnya di Stack Overflow tetapi akan lebih baik untuk mendapatkan pandangan khusus untuk jenis penyimpanan pesan umum.


758
2018-01-07 20:40


asal


Jawaban:


  • TEXT dan BLOB disimpan dari meja dengan meja hanya memiliki pointer ke lokasi penyimpanan yang sebenarnya.

  • VARCHAR disimpan sejajar dengan meja. VARCHAR lebih cepat ketika ukurannya masuk akal, tradeoff yang akan lebih cepat tergantung pada data Anda dan perangkat keras Anda, Anda ingin membandingkan skenario realworld dengan data Anda.

Memperbarui Apakah VARCHAR atau TEXT disimpan inline, atau off-record tergantung pada ukuran data, ukuran kolom, row_format, dan versi MySQL. Itu benar tidak tergantung pada "teks" vs "varchar".


759
2018-01-07 20:45



Bisakah Anda memprediksi berapa lama input pengguna?

VARCHAR (X)

Kasus: nama pengguna, email, negara, subjek, kata sandi


TEKS

Kasus: pesan, email, komentar, teks berformat, html, kode, gambar, tautan


MEDIUMTEXT

Kasus: tubuh json besar, buku pendek hingga menengah, string csv


LONGTEXT

Kasus: buku teks, program, tahun file log, harry potter dan piala api, penelitian ilmiah penebangan


415
2017-11-01 17:56



Hanya untuk memperjelas praktik terbaik:

  1. Pesan format teks hampir selalu disimpan sebagai TEXT (mereka akhirnya menjadi panjang secara arbitrer)

  2. Atribut string harus disimpan sebagai VARCHAR (nama pengguna tujuan, subjek, dll ...).

Saya mengerti bahwa Anda memiliki batas akhir depan, yang sangat bagus hingga tidak. * grin * Caranya adalah dengan memikirkan DB sebagai terpisah dari aplikasi yang terhubung dengannya. Hanya karena satu aplikasi menempatkan batas pada data, tidak berarti bahwa data secara intrinsik terbatas.

Apa itu tentang pesan itu sendiri yang memaksa mereka untuk tidak lebih dari 3000 karakter? Jika itu hanya kendala aplikasi yang sewenang-wenang (misalnya, untuk kotak teks atau sesuatu), gunakan a TEXT lapangan di lapisan data.


210
2018-01-07 21:53



Disclaimer: Saya bukan ahli MySQL ... tapi ini adalah pemahaman saya tentang masalah ini.

Saya pikir TEXT disimpan di luar baris mysql, sementara saya pikir TARUHAN disimpan sebagai bagian dari baris. Ada panjang baris maksimum untuk baris mysql .. sehingga Anda dapat membatasi berapa banyak data lain yang dapat Anda simpan berturut-turut dengan menggunakan VARCHAR.

Juga karena VARCHAR membentuk bagian dari baris, saya menduga bahwa pertanyaan yang melihat bidang itu akan sedikit lebih cepat daripada yang menggunakan potongan TEXT.


31
2018-01-07 20:47



Jawaban singkat:  Tidak praktis, kinerja, atau penyimpanan, perbedaan.

Jawaban panjang:

Pada dasarnya tidak ada perbedaan (di MySQL) antara VARCHAR(3000) (atau batas besar lainnya) dan TEXT. Yang pertama akan memotong pada 3000 karakter; yang terakhir akan terpotong pada 65535 byte. (Saya membuat perbedaan antara byte dan karakter karena karakter dapat mengambil beberapa byte.)

Untuk batas yang lebih kecil dalam VARCHAR, ada beberapa kelebihan TEXT.

  • "Lebih kecil" berarti 191, 255, 512, 767, atau 3072, dll, tergantung pada versi, konteks, dan CHARACTER SET.
  • INDEXes terbatas dalam seberapa besar kolom dapat diindeks. (767 atau 3072 byte; ini tergantung pada versi dan pengaturan)
  • Tabel menengah yang dibuat oleh kompleks SELECTs ditangani dalam dua cara berbeda - MEMORY (lebih cepat) atau MyISAM (lebih lambat). Ketika kolom 'besar' dilibatkan, teknik yang lebih lambat secara otomatis dipilih. (Perubahan signifikan datang di versi 8.0; jadi item peluru ini dapat berubah.)
  • Terkait dengan item sebelumnya, semuanya TEXT datatypes (sebagai lawan dari VARCHAR) melompat langsung ke MyISAM. Itu adalah, TINYTEXT secara otomatis lebih buruk untuk tabel temp yang dihasilkan daripada yang setara VARCHAR. (Tapi ini mengambil diskusi ke arah ketiga!)
  • VARBINARY seperti VARCHAR; BLOB seperti TEXT.

Bantahan terhadap jawaban lainnya

Pertanyaan asli menanyakan satu hal (yang mana tipe data yang digunakan); jawaban yang diterima menjawab sesuatu yang lain (penyimpanan tanpa arsip). Jawaban itu sekarang sudah ketinggalan zaman.

Ketika utas ini dimulai dan dijawab, hanya ada dua "format baris" di InnoDB. Segera setelah itu, dua format lainnya (DYNAMIC dan COMPRESSES) diperkenalkan.

Lokasi penyimpanan untuk TEXT dan VARCHAR() berdasarkan pada ukuran, tidak menyala nama datatype. Untuk sebuah diperbarui diskusi tentang penyimpanan on / off-record kolom teks / gumpalan besar, lihat ini .


3
2018-06-25 16:05



Jawaban sebelumnya tidak cukup mendesak untuk masalah utama: bahkan dalam pertanyaan yang sangat sederhana (SELECT t2. * FROM t1, t2 WHERE t2.id = t1.id ORDER BY t1.id) sebuah tabel sementara dapat diperlukan, dan jika bidang VARCHAR terlibat, dikonversi ke bidang CHAR di tabel sementara. Jadi jika Anda memiliki di meja Anda mengatakan 500.000 baris dengan bidang VARCHAR (65000), kolom ini saja akan menggunakan 6.5 * 5 * 10 ^ 9 byte. Tabel temp seperti itu tidak dapat ditangani dalam memori dan ditulis ke disk. Dampaknya bisa menjadi bencana besar.

Sumber (dengan metrik): https://nicj.net/mysql-text-vs-varchar-performance/ (Ini mengacu pada penanganan TEXT vs VARCHAR di mesin penyimpanan MyISAM "standar" (?). Mungkin berbeda pada yang lain, misalnya, InnoDB.)


1
2018-06-30 21:43