---
metadata:
  - name: generator
    content: Diplodoc Platform v5.50.6
alternate:
  - https://ytsaurus.tech/docs/en/user-guide/data-processing/spyt/best-practices.md
  - https://ytsaurus.tech/docs/ru/user-guide/data-processing/spyt/best-practices.md
---
> **Documentation Index:** Fetch the complete configuration index at https://ytsaurus.tech/docs/ru/llms.txt

<!-- source: ru/_includes/user-guide/data-processing/spyt/best-practices.md -->
# Best practices

- Каждый вызов `DROP` добавляет этап в плане, поэтому лучше избегать множественного исключения колонок. Эффективнее использовать одиночный `SELECT` с нужным набором колонок;
- использование операции `LIMIT` имеет свои особенности, влияющие на производительность. В Apache Spark она работает следующим образом: на каждой партиции выполняется стадия LocalLimit, её результат отправляется в shuffle и по всем собранным в shuffle результатам выполняется операция GlobalLimit. В случае использования `limit(x).collect()` или `take(x)` операция проходит в несколько итераций. Изначально количество участвующих партиций начинается с одной и с каждой итерацией умножается на значение параметра `spark.sql.limit.scaleUpFactor` (по умолчанию равно четырём). В случае использования операций `count()` или `write.save("/output/path")` операция LocalLimit выполняется на каждой партиции, и для больших датасетов с множеством партиций производительность limit ухудшается. Существует два варианта решения данной проблемы:
    - если значение limit является небольшим, таким, что результат выполнения take(x) помещается в памяти драйвера, можно использовать `limitedDf = spark.createDataFrame(spark.sparkContext.parallelize(df.take(10000)), df.schema)`;
    - в качестве альтернативы операции `LIMIT` можно использовать [TABLESAMPLE](https://spark.apache.org/docs/latest/sql-ref-syntax-qry-select-sampling.html). Но если указывать `TABLESAMPLE (x ROWS)`, то в плане выполнения такой вызов будет эквивалентен `LIMIT x`.
- Для чтения данных, использующих Hive-совместимую схему партиционирования по директориям в Кипарисе, опция `recursiveFileLookup` должна явно быть выставлена в `false`: `spark.read.option("recursiveFileLookup", "false")`. В SPYT она по умолчанию выставлена в `true` для унификации с поведением YQL и CHYT.
<!-- endsource: ru/_includes/user-guide/data-processing/spyt/best-practices.md -->
