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

> Documentación de la cláusula PREWHERE

# Cláusula PREWHERE

PREWHERE es una optimización para aplicar el filtrado de forma más eficiente. Está habilitada de forma predeterminada aunque la cláusula `PREWHERE` no se especifique explícitamente. Funciona moviendo automáticamente parte de la condición [WHERE](/es/reference/statements/select/where) a la etapa de prewhere. La función de la cláusula `PREWHERE` es únicamente controlar esta optimización si cree que sabe hacerlo mejor que como ocurre de forma predeterminada.

Con la optimización de prewhere, primero solo se leen las columnas necesarias para ejecutar la expresión de prewhere. Después, se leen las demás columnas necesarias para ejecutar el resto de la consulta, pero solo en aquellos bloques en los que la expresión de prewhere es `true` al menos para algunas filas. Si hay muchos bloques en los que la expresión de prewhere es `false` para todas las filas y prewhere necesita menos columnas que otras partes de la consulta, esto a menudo permite leer muchos menos datos del disco para ejecutar la consulta.

<div id="controlling-prewhere-manually">
  ## Control de PREWHERE manualmente
</div>

La cláusula tiene el mismo significado que la cláusula `WHERE`. La diferencia está en qué datos se leen de la tabla. Cuando se controla manualmente `PREWHERE` para condiciones de filtrado que se usan en una minoría de las columnas de la consulta, pero que ofrecen un filtrado de datos eficaz, se reduce el volumen de datos que se debe leer.

Una consulta puede especificar `PREWHERE` y `WHERE` simultáneamente. En este caso, `PREWHERE` precede a `WHERE`.

Si la configuración [optimize\_move\_to\_prewhere](/es/reference/settings/session-settings#optimize_move_to_prewhere) está establecida en 0, se desactivan las heurísticas que mueven automáticamente partes de las expresiones de `WHERE` a `PREWHERE`.

Si la consulta tiene el modificador [FINAL](/es/reference/statements/select/from#final-modifier), la optimización de `PREWHERE` no siempre es correcta. Solo se habilita si ambas configuraciones [optimize\_move\_to\_prewhere](/es/reference/settings/session-settings#optimize_move_to_prewhere) y [optimize\_move\_to\_prewhere\_if\_final](/es/reference/settings/session-settings#optimize_move_to_prewhere_if_final) están activadas.

<Note>
  La sección `PREWHERE` se ejecuta antes de `FINAL`, por lo que los resultados de las consultas `FROM ... FINAL` pueden verse sesgados al usar `PREWHERE` con campos que no están en la sección `ORDER BY` de una tabla.
</Note>

<div id="limitations">
  ## Limitaciones
</div>

`PREWHERE` solo se admite en tablas de la familia [\*MergeTree](/es/reference/engines/table-engines/mergetree-family/index).

<div id="example">
  ## Ejemplo
</div>

```sql theme={null}
CREATE TABLE mydata
(
    `A` Int64,
    `B` Int8,
    `C` String
)
ENGINE = MergeTree
ORDER BY A AS
SELECT
    number,
    0,
    if(number between 1000 and 2000, 'x', toString(number))
FROM numbers(10000000);

SELECT count()
FROM mydata
WHERE (B = 0) AND (C = 'x');

1 row in set. Elapsed: 0.074 sec. Processed 10.00 million rows, 168.89 MB (134.98 million rows/s., 2.28 GB/s.)

-- habilitemos el tracing para ver qué predicados se mueven a PREWHERE
set send_logs_level='debug';

MergeTreeWhereOptimizer: condition "B = 0" moved to PREWHERE  
-- ClickHouse mueve automáticamente `B = 0` a PREWHERE, pero no tiene sentido porque B siempre es 0.

-- Movamos el otro predicado `C = 'x'` 

SELECT count()
FROM mydata
PREWHERE C = 'x'
WHERE B = 0;

1 row in set. Elapsed: 0.069 sec. Processed 10.00 million rows, 158.89 MB (144.90 million rows/s., 2.30 GB/s.)

-- Esta consulta con `PREWHERE` manual procesa ligeramente menos datos: 158.89 MB VS 168.89 MB
```
