¿Debo agregar un límite de longitud arbitrario a las columnas VARCHAR?


35

Según los documentos de PostgreSQL , no hay diferencia de rendimiento entre VARCHAR, VARCHAR(n)y TEXT.

¿Debo agregar un límite de longitud arbitrario a una columna de nombre o dirección ?

Editar: No es un tonto de:

Sé que el CHARtipo es una reliquia del pasado y estoy interesado no solo en el rendimiento, sino también en otros pros y contras como Erwin en su sorprendente respuesta.

Respuestas:


45

La respuesta es no .
No agregue un modificador de longitud varcharsi puede evitarlo. La mayoría de las veces, en realidad no necesita una restricción de longitud. Solo utilícelo textpara todos los datos de los personajes. Haga eso varchar(sin modificador de longitud) si necesita mantenerse compatible con RDBMS que no tiene text.

El rendimiento es casi el mismo: textes un poco más rápido en situaciones excepcionales y guarda los ciclos para verificar la longitud.

Si realmente necesita imponer una longitud máxima, aún use texty agregue una restricción de verificación para eso:

ALTER TABLE tbl ADD CONSTRAINT tbl_col_len CHECK (length(col) < 51);

Puede modificar o eliminar dicha restricción en cualquier momento sin tener que meterse con la definición de la tabla y todos los objetos dependientes (vistas, funciones, teclas foráneas, ...)

Con los modificadores de longitud simplemente te encuentras con problemas como este o esto o esto ...

PostgreSQL 9.1 introdujo una nueva característica para aliviar un poco el dolor. Cito las notas de la versión aquí :

Permitir ALTER TABLE ... SET DATA TYPEevitar reescrituras de tablas en casos apropiados (Noah Misch, Robert Haas)

Por ejemplo, convertir una varcharcolumna en texto ya no requiere una reescritura de la tabla. Sin embargo, aumentar la restricción de longitud en una varcharcolumna aún requiere una reescritura de la tabla.


Creo que esta respuesta sería mucho mejor si simplemente fuera "no, no agregue límites arbitrarios a una base de datos real". Siento que mucha de esta respuesta necesita correcciones e información adicional, pero que está totalmente fuera de tema y distraería su conclusión con la que estoy totalmente de acuerdo.
Evan Carroll

Sí, todo basado en versiones de Postgres anteriores a 9.1 - hace 6 años. Un poco polvoriento por ahora, pero el consejo básico sigue siendo bueno.
Erwin Brandstetter

¿Es una buena o mala idea agregar una restricción de verificación para cada columna de texto con el propósito de una verificación de la cordura y asegurar que un error en el cliente no use todo el espacio en disco de la base de datos insertando un texto muy grande?
Código

@Code: es una opción viable. Si tiene muchas columnas con la misma restricción, considere los dominios . O, varchar(n)después de todo, por simplicidad, si las desventajas no suelen afectarlo. (El límite no es arbitrario en su caso si desea imponer una longitud máxima real).
Erwin Brandstetter

12

Si ve el límite de longitud como una especie de restricción de verificación para asegurarse de validar los datos, entonces sí agregue uno. En realidad, es posible que no desee utilizar una definición de longitud, sino una restricción de verificación real, para que el cambio del límite sea más rápido.

Para cambiar (aumentar) un límite de longitud, debe ejecutar uno ALTER TABLEque puede tardar mucho tiempo en finalizar (debido a una posible reescritura de la tabla) durante el cual es necesario un bloqueo exclusivo de la tabla.

Cambiar (es decir, eliminar y volver a crear) una restricción de verificación es una operación muy breve y solo requiere leer los datos de la tabla, no cambiará ninguna fila. Por lo tanto, será mucho más rápido (lo que a su vez significa que el bloqueo exclusivo de la tabla se mantendrá durante un período de tiempo mucho más corto).

Durante la operación no hay diferencia alguna entre a text, a varcharo una varchar(5000)columna.


Por pura curiosidad, ¿por qué cree que esta verificación de longitud no se puede hacer en una aplicación cliente mientras se capturan datos?
PirateApp

44
@PirateApp: porque muy a menudo habrá más de una aplicación o alguna fuente de datos externa (piense en las importaciones por lotes nocturnas). Y casi siempre la base de datos (y los datos) viven más de una aplicación.
a_horse_with_no_name

2

La pregunta es específicamente si se agrega un límite de longitud arbitrario a las columnas VARCHAR?

Para eso, la respuesta es simplemente "no". No hay nada que pueda justificar la adición de un límite arbitrario como lo haría en bases de datos inferiores que admiten varchar(max)o usan convenciones como varchar(255). Sin embargo, si la especificación aborda un límite, creo que la respuesta se vuelve mucho más compleja, especialmente en las versiones modernas de PostgreSQL. Y, por eso, me inclinaría hacia .

En mi opinión, el límite es una elección acertada si la especificación lo requiere. Especialmente para cargas de trabajo más razonables. Si por ninguna otra razón, para preservar metadatos.

De mi respuesta aquí, indexe el rendimiento de CHAR vs VARCHAR (Postgres) , donde abordo el valor de los metadatos.

Si encontrara una especificación que tuviera claves de texto de longitud variable que fueran significativas y confiara en tener una longitud máxima constante, varchartambién la usaría . Sin embargo, no puedo pensar en nada que se ajuste a ese criterio.


1

Parece que puede haber alguna diferencia de rendimiento si VARCHARse usa regularmente para almacenar cadenas muy grandes, ya que "las cadenas largas son comprimidas automáticamente por el sistema" y "los valores muy largos también se almacenan en tablas de fondo". Teóricamente, esto significaría que un gran volumen de solicitudes para un campo de cadena muy largo sería más lento que para un campo de cadena corto. Probablemente nunca se encuentre con este problema, ya que los nombres y las direcciones no serán muy largos.

Sin embargo, dependiendo de cómo esté utilizando estas cadenas fuera de su base de datos, es posible que desee agregar un límite práctico para evitar el abuso del sistema. Por ejemplo, si está mostrando el nombre y la dirección en un formulario en algún lugar, es posible que no pueda mostrar un párrafo completo de texto en el campo "nombre", por lo que tendría sentido limitar la columna de nombre a algo así como 500 caracteres.


1
AFAIK no hay diferencia en TOSTAR varchar y campos de texto.
dezso

VARCHARes azúcar puramente sintáctico para TEXTen Postgres, no hay diferencia en el manejo de almacenamiento; el almacenamiento de la tabla de compresión frente a fondo que menciona se realiza en función de la longitud real de los datos en la columna y no en los metadatos de la columna. Las columnas TEXT se almacenan internamente como una varlenaestructura C (que es una matriz de longitud variable con los primeros 4 bytes que almacenan la longitud en crear / actualizar) y es esta estructura la que está optimizada en función de su longitud.
cowbert
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.