> ## Documentation Index
> Fetch the complete documentation index at: https://private-7c7dfe99-parallel-read-in-order-multi-part.mintlify.site/llms.txt
> Use this file to discover all available pages before exploring further.

> Documentación de la cláusula DISTINCT

# DISTINCT

Si se especifica `SELECT DISTINCT`, en el resultado de una consulta solo permanecerán las filas únicas. Es decir, de cada conjunto de filas completamente idénticas en el resultado, solo permanecerá una.

Puede especificar la lista de columnas que deben tener valores únicos: `SELECT DISTINCT ON (column1, column2,...)`. Si no se especifican las columnas, se tendrán en cuenta todas.

Considere la tabla:

```text theme={null}
┌─a─┬─b─┬─c─┐
│ 1 │ 1 │ 1 │
│ 1 │ 1 │ 1 │
│ 2 │ 2 │ 2 │
│ 2 │ 2 │ 2 │
│ 1 │ 1 │ 2 │
│ 1 │ 2 │ 2 │
└───┴───┴───┘
```

Usar `DISTINCT` sin especificar columnas:

```sql theme={null}
SELECT DISTINCT * FROM t1;
```

```text theme={null}
┌─a─┬─b─┬─c─┐
│ 1 │ 1 │ 1 │
│ 2 │ 2 │ 2 │
│ 1 │ 1 │ 2 │
│ 1 │ 2 │ 2 │
└───┴───┴───┘
```

Uso de `DISTINCT` con columnas específicas:

```sql theme={null}
SELECT DISTINCT ON (a,b) * FROM t1;
```

```text theme={null}
┌─a─┬─b─┬─c─┐
│ 1 │ 1 │ 1 │
│ 2 │ 2 │ 2 │
│ 1 │ 2 │ 2 │
└───┴───┴───┘
```

## DISTINCT y ORDER BY

ClickHouse permite usar las cláusulas `DISTINCT` y `ORDER BY` para columnas diferentes en una misma consulta. La cláusula `DISTINCT` se ejecuta antes que la cláusula `ORDER BY`.

Considere la tabla:

```text theme={null}
┌─a─┬─b─┐
│ 2 │ 1 │
│ 1 │ 2 │
│ 3 │ 3 │
│ 2 │ 4 │
└───┴───┘
```

Selección de datos:

```sql theme={null}
SELECT DISTINCT a FROM t1 ORDER BY b ASC;
```

```text theme={null}
┌─a─┐
│ 2 │
│ 1 │
│ 3 │
└───┘
```

Selección de datos con diferentes direcciones de ordenación:

```sql theme={null}
SELECT DISTINCT a FROM t1 ORDER BY b DESC;
```

```text theme={null}
┌─a─┐
│ 3 │
│ 1 │
│ 2 │
└───┘
```

La fila `2, 4` se truncó antes de ordenar.

Tenga en cuenta esta particularidad de la implementación al escribir consultas.

## Tratamiento de NULL

`DISTINCT` funciona con [NULL](/es/reference/syntax#null) como si `NULL` fuera un valor específico y `NULL==NULL`. En otras palabras, en los resultados de `DISTINCT`, las distintas combinaciones con `NULL` aparecen solo una vez. Esto difiere del tratamiento de `NULL` en la mayoría de los demás contextos.

## Alternativas

Es posible obtener el mismo resultado aplicando [GROUP BY](/es/reference/statements/select/group-by) al mismo conjunto de valores especificado en la cláusula `SELECT`, sin usar ninguna función de agregación. Sin embargo, hay algunas diferencias con respecto al enfoque de `GROUP BY`:

* `DISTINCT` se puede aplicar junto con `GROUP BY`.
* Antes de que comience la ejecución externa, una consulta sin [ORDER BY](/es/reference/statements/select/order-by) puede detenerse en cuanto haya leído suficientes filas distintas para satisfacer el [LIMIT](/es/reference/statements/select/limit).
* Antes de que comience la ejecución externa y cuando se omite `ORDER BY`, un intervalo [`LIMIT ... AFTER ... UNTIL`](/es/reference/statements/select/limit#limit-after-until) sin `ALL` también puede detener la consulta una vez que el intervalo ha finalizado.
* Los bloques de datos se generan a medida que se procesan hasta que comienza la ejecución externa.

## DISTINCT en memoria externa

`DISTINCT` puede escribir datos temporales en disco para procesar conjuntos de valores únicos demasiado
grandes como para mantenerlos en memoria. Esto implica E/S de disco adicional y puede ralentizar las consultas.

Hay dos configuraciones que controlan cuándo comienza el volcado a disco:

* `max_bytes_before_external_distinct` establece un umbral, en bytes, de la memoria total de la consulta. Su valor
  predeterminado es `0` (desactivado).
* `max_bytes_ratio_before_external_distinct` establece una fracción de la memoria disponible según los límites del servidor
  o del usuario, medida al inicio de la ejecución. Su valor predeterminado es `0.5` y no tiene efecto cuando
  no se aplica ninguno de esos límites.

Cuando ambos umbrales son aplicables, se utiliza el menor. Establezca ambas configuraciones en `0` para desactivar el volcado a disco.

`max_memory_usage` no afecta a la proporción. Para configurar el volcado a disco en relación con un memory limit de consulta,
establezca un umbral absoluto por debajo de ese límite. Por ejemplo, esta consulta usa un umbral de volcado de 16 MiB
con un memory limit de consulta de 256 MiB:

```sql theme={null}
SELECT DISTINCT number % 1000000 AS id
FROM numbers(2000000)
SETTINGS
    max_bytes_before_external_distinct = 16777216,
    max_bytes_ratio_before_external_distinct = 0,
    max_memory_usage = 268435456;
```

Estos umbrales no limitan el uso de memoria. Deje margen para el resto del procesamiento de la consulta y para el propio volcado a disco. El volcado también puede iniciarse antes si hay presión de memoria.

Se pueden devolver filas antes del volcado, y un `LIMIT` satisfecho en esta etapa puede finalizar la consulta de forma anticipada.
Una vez que comienza el volcado, hay que leer el resto de la entrada antes de poder devolver los resultados pendientes.
Si la consulta incluye `ORDER BY`, esos resultados se devuelven en el orden solicitado.

Cuando `DISTINCT` utiliza una entrada ordenada por un prefijo de sus claves, no realiza volcado a disco. Aun así, un grupo grande de filas con el mismo prefijo puede consumir una cantidad considerable de memoria.

Al igual que con `optimize_distinct_in_order`, el volcado puede deduplicar valores de coma flotante que tienen representaciones binarias distintas pero que se comparan como iguales, incluidos `0.0` y `-0.0`, o valores `NaN` con cargas útiles diferentes.
