Перейти к основному содержанию
Создаёт новую таблицу. Этот запрос может иметь различные синтаксические формы в зависимости от сценария использования. По умолчанию таблицы создаются только на текущем сервере. Распределённые DDL-запросы реализованы в виде предложения ON CLUSTER, которое описано отдельно.

Варианты синтаксиса

С явной схемой

CREATE TABLE [IF NOT EXISTS] [db.]table_name [ON CLUSTER cluster]
(
    name1 [type1] [NULL|NOT NULL] [DEFAULT|MATERIALIZED|EPHEMERAL|ALIAS expr1] [COMMENT 'comment for column'] [compression_codec] [TTL expr1],
    name2 [type2] [NULL|NOT NULL] [DEFAULT|MATERIALIZED|EPHEMERAL|ALIAS expr2] [COMMENT 'comment for column'] [compression_codec] [TTL expr2],
    ...
) ENGINE = engine
  [COMMENT 'comment for table']
Создаёт таблицу с именем table_name в базе данных db или в текущей базе данных, если db не задана, со структурой, указанной в скобках, и движком engine. Структура таблицы представляет собой список описаний столбцов, вторичных индексов, проекций и ограничений. Если первичный ключ поддерживается движком, он указывается как параметр движка таблицы. В простейшем случае описание столбца имеет вид name type. Пример: RegionID UInt32. Для значений по умолчанию также можно задавать выражения (см. ниже). При необходимости можно указать первичный ключ с одним или несколькими ключевыми выражениями. Для столбцов и таблицы можно добавлять комментарии.

Со схемой существующей таблицы

ClickHouse позволяет копировать схему и данные существующей таблицы. Чтобы скопировать схему существующей таблицы:
CREATE TABLE [IF NOT EXISTS] [db2.]table_clone AS [db.]table [ENGINE = engine]
Это создает таблицу с такой же структурой, как у другой таблицы.

Со схемой и данными существующей таблицы

Чтобы реплицировать схему и данные существующей таблицы:
CREATE TABLE [IF NOT EXISTS] [db2.]table_clone CLONE AS [db.]table [ENGINE = engine]
Это создаёт таблицу с той же схемой и теми же данными, что и существующая таблица. После создания новой таблицы к ней присоединяются все партиции из db.table. Иными словами, при создании данные из db.table клонируются в db2.table_clone. Этот запрос эквивалентен следующему:
CREATE TABLE [IF NOT EXISTS] [db2.]table_clone AS [db.]table [ENGINE = engine];
ALTER TABLE [db2.]table_clone ATTACH PARTITION ALL FROM [db.]table;
Для обеих возможностей можно указать для таблицы другой движок. Если движок не указан, будет использоваться тот же движок, что и у исходной таблицы (db.table).

Из табличной функции

CREATE TABLE [IF NOT EXISTS] [db.]table_name AS table_function()
Создаёт таблицу с тем же результатом, что и указанная табличная функция. Созданная таблица также будет работать так же, как соответствующая табличная функция.

Из запроса SELECT

CREATE TABLE [IF NOT EXISTS] [db.]table_name[(name1 [type1], name2 [type2], ...)] ENGINE = engine AS SELECT ...
Создаёт таблицу со структурой, аналогичной результату запроса SELECT, с движком engine и заполняет её данными из SELECT. Также можно явно указать описание столбцов. Если таблица уже существует и указано IF NOT EXISTS, запрос не выполнит никаких действий. В запросе после предложения ENGINE могут следовать и другие предложения. Подробную документацию о том, как создавать таблицы, см. в описаниях движков таблиц. Пример
Query
CREATE TABLE t1 (x String) ENGINE = Memory AS SELECT 1;
SELECT x, toTypeName(x) FROM t1;
Response
┌─x─┬─toTypeName(x)─┐
│ 1 │ String        │
└───┴───────────────┘

Модификаторы NULL и NOT NULL

Модификаторы NULL и NOT NULL, указанные после типа данных в определении столбца, соответственно разрешают или запрещают делать его Nullable. Если тип не Nullable и указан NULL, он будет трактоваться как Nullable; если указан NOT NULL, то нет. Например, INT NULL — то же самое, что Nullable(INT). Если тип — Nullable и указаны модификаторы NULL или NOT NULL, будет сгенерировано исключение. См. также настройку data_type_default_nullable.

Значения по умолчанию

Описание столбца может задавать выражение значения по умолчанию в форме DEFAULT expr, MATERIALIZED expr или ALIAS expr. Пример: URLDomain String DEFAULT domain(URL). Выражение expr необязательно. Если оно опущено, тип столбца должен быть указан явно, а значением по умолчанию будет 0 для числовых столбцов, '' (пустая строка) для строковых столбцов, [] (пустой массив) для столбцов типа Array, 1970-01-01 для столбцов с типом Date или NULL для столбцов с типом Nullable. Тип столбца со значением по умолчанию можно не указывать — в этом случае он выводится из типа expr. Например, тип столбца EventDate DEFAULT toDate(EventTime) будет Date. Если указаны и тип данных, и выражение значения по умолчанию, неявно добавляется функция приведения типов, которая преобразует выражение к указанному типу. Пример: Hits UInt32 DEFAULT 0 внутри представляется как Hits UInt32 DEFAULT toUInt32(0). Выражение значения по умолчанию expr может ссылаться на произвольные столбцы таблицы и константы. ClickHouse проверяет, что изменения структуры таблицы не приводят к появлению циклов при вычислении выражений. Для INSERT также проверяется, что выражения могут быть вычислены, то есть что переданы все столбцы, на основе которых их можно вычислить.

DEFAULT

DEFAULT expr Обычное значение по умолчанию. Если значение такого столбца не указано в запросе INSERT, оно вычисляется на основе expr. Пример:
CREATE OR REPLACE TABLE test
(
    id UInt64,
    updated_at DateTime DEFAULT now(),
    updated_at_date Date DEFAULT toDate(updated_at)
)
ENGINE = MergeTree
ORDER BY id;

INSERT INTO test (id) VALUES (1);

SELECT * FROM test;
┌─id─┬──────────updated_at─┬─updated_at_date─┐
12023-02-24 17:06:462023-02-24
└────┴─────────────────────┴─────────────────┘

MATERIALIZED

MATERIALIZED expr Материализованное выражение. Значения таких столбцов автоматически вычисляются в соответствии с указанным материализованным выражением при вставке строк. Эти значения нельзя явно задавать в INSERT. Кроме того, такие столбцы со значением по умолчанию не включаются в результат SELECT *. Это сделано для сохранения инварианта, согласно которому результат SELECT * всегда можно вставить обратно в таблицу с помощью INSERT. Это поведение можно отключить с помощью настройки asterisk_include_materialized_columns. Пример:
CREATE OR REPLACE TABLE test
(
    id UInt64,
    updated_at DateTime MATERIALIZED now(),
    updated_at_date Date MATERIALIZED toDate(updated_at)
)
ENGINE = MergeTree
ORDER BY id;

INSERT INTO test VALUES (1);

SELECT * FROM test;
┌─id─┐
1
└────┘

SELECT id, updated_at, updated_at_date FROM test;
┌─id─┬──────────updated_at─┬─updated_at_date─┐
12023-02-24 17:08:082023-02-24
└────┴─────────────────────┴─────────────────┘

SELECT * FROM test SETTINGS asterisk_include_materialized_columns=1;
┌─id─┬──────────updated_at─┬─updated_at_date─┐
12023-02-24 17:08:082023-02-24
└────┴─────────────────────┴─────────────────┘

EPHEMERAL

EPHEMERAL [expr] Эфемерный столбец. Столбцы этого типа не хранятся в таблице, и их нельзя использовать в SELECT. Единственное назначение эфемерных столбцов — формировать на их основе выражения значений по умолчанию для других столбцов. При вставке без явно указанных столбцов столбцы этого типа будут пропущены. Это нужно, чтобы сохранить инвариант: результат SELECT * всегда можно вставить обратно в таблицу с помощью INSERT. Пример:
CREATE OR REPLACE TABLE test
(
    id UInt64,
    unhexed String EPHEMERAL,
    hexed FixedString(4) DEFAULT unhex(unhexed)
)
ENGINE = MergeTree
ORDER BY id;

INSERT INTO test (id, unhexed) VALUES (1, '5a90b714');

SELECT
    id,
    hexed,
    hex(hexed)
FROM test
FORMAT Vertical;

Row 1:
──────
id:         1
hexed:      Z��
hex(hexed): 5A90B714

ALIAS

ALIAS expr Вычисляемые столбцы (синоним). Столбцы этого типа не хранятся в таблице, и в них нельзя вставлять значения. Когда запросы SELECT явно обращаются к столбцам этого типа, значение вычисляется во время выполнения запроса из expr. По умолчанию SELECT * исключает столбцы ALIAS. Это поведение можно отключить с помощью настройки asterisk_include_alias_columns. При использовании запроса ALTER для добавления новых столбцов старые данные для этих столбцов не записываются. Вместо этого при чтении старых данных, в которых нет значений для новых столбцов, выражения по умолчанию вычисляются на лету. Однако если для вычисления выражений требуются другие столбцы, не указанные в запросе, эти столбцы также будут прочитаны, но только для тех блоков данных, где это необходимо. Если вы добавите новый столбец в таблицу, а затем измените его выражение по умолчанию, значения, используемые для старых данных, изменятся (для данных, значения которых не были сохранены на диске). Обратите внимание, что при выполнении фоновых слияний данные для столбцов, отсутствующих в одной из сливающихся частей, записываются в слитую часть. Невозможно задать значения по умолчанию для элементов во вложенных структурах данных.
CREATE OR REPLACE TABLE test
(
    id UInt64,
    size_bytes Int64,
    size String ALIAS formatReadableSize(size_bytes)
)
ENGINE = MergeTree
ORDER BY id;

INSERT INTO test VALUES (1, 4678899);

SELECT id, size_bytes, size FROM test;
┌─id─┬─size_bytes─┬─size─────┐
146788994.46 MiB │
└────┴────────────┴──────────┘

SELECT * FROM test SETTINGS asterisk_include_alias_columns=1;
┌─id─┬─size_bytes─┬─size─────┐
146788994.46 MiB │
└────┴────────────┴──────────┘

Первичный ключ

При создании таблицы можно определить первичный ключ. Первичный ключ можно задать двумя способами:
  • В списке столбцов
CREATE TABLE [db.]table_name
(
    name1 type1, name2 type2, ...,
    PRIMARY KEY(expr1[, expr2,...])
)
ENGINE = engine;
  • Вне списка столбцов
CREATE TABLE [db.]table_name
(
    name1 type1, name2 type2, ...
)
ENGINE = engine
PRIMARY KEY(expr1[, expr2,...]);
Нельзя использовать оба способа в одном запросе.

Ограничения

Наряду с описанием столбцов можно также задавать ограничения:

CONSTRAINT

CREATE TABLE [IF NOT EXISTS] [db.]table_name [ON CLUSTER cluster]
(
    name1 [type1] [DEFAULT|MATERIALIZED|ALIAS expr1] [compression_codec] [TTL expr1],
    ...
    CONSTRAINT constraint_name_1 CHECK boolean_expr_1,
    ...
) ENGINE = engine
boolean_expr_1 может быть любым логическим выражением. Если для таблицы заданы ограничения, каждое из них будет проверяться для каждой строки в запросе INSERT. Если какое-либо ограничение нарушено, сервер сгенерирует исключение с именем ограничения и выражением проверки. Добавление большого количества ограничений может негативно сказаться на производительности крупных запросов INSERT.

ASSUME

Предложение ASSUME используется для задания CONSTRAINT для таблицы, которое считается истинным. Затем это ограничение может использоваться оптимизатором для повышения производительности SQL-запросов. Рассмотрим пример, в котором ASSUME CONSTRAINT используется при создании таблицы users_a:
CREATE TABLE users_a (
    uid Int16, 
    name String, 
    age Int16, 
    name_len UInt8 MATERIALIZED length(name), 
    CONSTRAINT c1 ASSUME length(name) = name_len
) 
ENGINE=MergeTree 
ORDER BY (name_len, name);
Здесь ASSUME CONSTRAINT используется, чтобы указать, что функция length(name) всегда равна значению столбца name_len. Это означает, что всякий раз, когда в запросе вызывается length(name), ClickHouse может заменить её на name_len, что должно работать быстрее, поскольку не требует вызова функции length(). Затем, при выполнении запроса SELECT name FROM users_a WHERE length(name) < 5;, ClickHouse может оптимизировать его до SELECT name FROM users_a WHERE name_len < 5; благодаря ASSUME CONSTRAINT. Это может ускорить выполнение запроса, поскольку не нужно вычислять длину name для каждой строки. ASSUME CONSTRAINT не обеспечивает соблюдение ограничения, а лишь сообщает оптимизатору, что ограничение выполняется. Если ограничение на самом деле не выполняется, результаты запросов могут быть некорректными. Поэтому использовать ASSUME CONSTRAINT следует только в том случае, если вы уверены, что ограничение действительно выполняется.

Выражение TTL

Определяет срок хранения значений. Может быть указано только для таблиц семейства MergeTree. Подробное описание см. в разделе TTL для столбцов и таблиц.

Кодеки сжатия столбцов

По умолчанию в самоуправляемой версии ClickHouse используется сжатие lz4, а в ClickHouse Cloud — zstd. Для семейства движков MergeTree метод сжатия по умолчанию можно изменить в разделе compression конфигурации сервера. Метод сжатия также можно задать для каждого отдельного столбца в запросе CREATE TABLE.
CREATE TABLE codec_example
(
    dt Date CODEC(ZSTD),
    ts DateTime CODEC(LZ4HC),
    float_value Float32 CODEC(NONE),
    double_value Float64 CODEC(LZ4HC(9)),
    value Float32 CODEC(Delta, ZSTD)
)
ENGINE = <Engine>
...
Кодек Default можно указать, чтобы использовать сжатие по умолчанию, которое во время выполнения может зависеть от различных настроек (и свойств данных). Пример: value UInt64 CODEC(Default) — то же самое, что и отсутствие указания кодека. Также можно удалить текущий CODEC из столбца и использовать сжатие по умолчанию из config.xml:
ALTER TABLE codec_example MODIFY COLUMN float_value CODEC(Default);
Кодеки можно объединять в цепочку, например, CODEC(Delta, Default).
Файлы базы данных ClickHouse нельзя распаковать с помощью внешних утилит, таких как lz4. Вместо этого используйте специальную утилиту clickhouse-compressor.
Сжатие поддерживается для следующих движков таблиц:
  • Семейство MergeTree. Поддерживает кодеки сжатия для столбцов и выбор метода сжатия по умолчанию через настройки compression.
  • Семейство Log. По умолчанию использует метод сжатия lz4 и поддерживает кодеки сжатия для столбцов.
  • Set. Поддерживается только сжатие по умолчанию.
  • Join. Поддерживается только сжатие по умолчанию.
ClickHouse поддерживает кодеки общего назначения и специализированные кодеки.

Кодеки общего назначения

NONE

NONE — без сжатия.

LZ4

LZ4 — алгоритм сжатия данных без потерь, используемый по умолчанию. Использует быстрое сжатие LZ4.

LZ4HC

LZ4HC[(level)] — алгоритм LZ4 HC (высокая степень сжатия) с настраиваемым уровнем. Уровень по умолчанию: 9. Если задано level <= 0, используется уровень по умолчанию. Допустимые уровни: [1, 12]. Рекомендуемый диапазон уровней: [4, 9].

ZSTD

ZSTD[(level)]алгоритм сжатия ZSTD с настраиваемым level. Возможные уровни: [1, 22]. Уровень по умолчанию: 1. Высокие уровни сжатия полезны в асимметричных сценариях, например когда данные сжимаются один раз, а распаковываются многократно. Чем выше уровень, тем лучше сжатие и тем выше нагрузка на CPU.

Устарело: ZSTD_QAT

Устарел: DEFLATE_QPL

Специализированные кодеки

Эти кодеки предназначены для повышения эффективности сжатия за счет использования определенных особенностей данных. Некоторые из них сами по себе данные не сжимают, а вместо этого предварительно обрабатывают их так, чтобы на втором этапе сжатия кодек общего назначения мог обеспечить более высокую степень сжатия.

Delta

Delta(delta_bytes) — метод сжатия, при котором исходные значения заменяются разностью двух соседних значений, кроме первого, которое остаётся без изменений. delta_bytes — максимальный размер исходных значений; значение по умолчанию — sizeof(type). Указывать delta_bytes в качестве аргумента не рекомендуется, и в будущем эта возможность будет удалена. Delta — кодек подготовки данных, то есть его нельзя использовать самостоятельно.

DoubleDelta

DoubleDelta(bytes_size) — вычисляет дельту дельт и записывает её в компактном двоичном виде. bytes_size имеет смысл, аналогичный delta_bytes в кодеке Delta. Указывать bytes_size в качестве аргумента не рекомендуется, и в будущих релизах его поддержка будет удалена. Наилучшее сжатие достигается для монотонных последовательностей с постоянным шагом, например для данных временных рядов. Может использоваться с любым числовым типом. Реализует алгоритм, используемый в Gorilla TSDB, с расширением для поддержки 64-битных типов. Использует 1 дополнительный бит для 32-битных дельт: 5-битные префиксы вместо 4-битных. Дополнительные сведения см. в разделе Compressing Time Stamps статьи Gorilla: A Fast, Scalable, In-Memory Time Series Database. DoubleDelta — это кодек подготовки данных, то есть его нельзя использовать самостоятельно.

GCD

GCD() - - вычисляет наибольший общий делитель (GCD) значений в столбце, а затем делит каждое значение на GCD. Может использоваться со столбцами целочисленных, десятичных типов и типов даты/времени. Этот кодек хорошо подходит для столбцов со значениями, которые изменяются (увеличиваются или уменьшаются) с шагом, кратным GCD, например 24, 28, 16, 24, 8, 24 (GCD = 4). GCD — это кодек подготовки данных, то есть его нельзя использовать самостоятельно.

Gorilla

Gorilla(bytes_size) — вычисляет XOR между текущим и предыдущим значением с плавающей запятой и записывает результат в компактной двоичной форме. Чем меньше разница между последовательными значениями, то есть чем медленнее меняются значения серии, тем выше степень сжатия. Реализует алгоритм, используемый в Gorilla TSDB, с расширением для поддержки 64-битных типов. Возможные значения bytes_size: 1, 2, 4, 8; значение по умолчанию — sizeof(type), если оно равно 1, 2, 4 или 8. Во всех остальных случаях используется 1. Дополнительные сведения см. в разделе 4.1 статьи Gorilla: A Fast, Scalable, In-Memory Time Series Database.

ALP

ALP() — адаптивное сжатие без потерь для данных с плавающей точкой на основе десятичного масштабирования. ALP пытается представить каждое значение как точное целое число, масштабированное степенями десяти, а затем сжимает полученные целые числа с помощью Frame-of-Reference и побитовой упаковки. Значения, которые нельзя представить точно, сохраняются как необработанные исключения. Лучше всего подходит для чисел, происходящих из десятичных значений (например, измерений или денежных сумм). Поддерживает Float32 и Float64. Подробности см. в статье ALP: Adaptive lossless floating-point compression.
Этот кодек является экспериментальным, и для его использования требуется SET allow_experimental_codecs = 1.

FPC

FPC(level, float_size) — многократно предсказывает следующее значение с плавающей запятой в последовательности, используя лучший из двух предикторов, затем выполняет XOR фактического и предсказанного значений и сжимает результат за счёт ведущих нулей. Как и Gorilla, этот кодек эффективен при хранении серии значений с плавающей запятой, которые изменяются медленно. Для 64-битных значений (double) FPC быстрее, чем Gorilla; для 32-битных значений результат может отличаться. Возможные значения level: 1–28, значение по умолчанию — 12. Возможные значения float_size: 4, 8; значение по умолчанию — sizeof(type), если тип — Float. Во всех остальных случаях это 4. Подробное описание алгоритма см. в статье High Throughput Compression of Double-Precision Floating-Point Data.

T64

T64 — метод сжатия, при котором отбрасываются неиспользуемые старшие биты значений в целочисленных типах данных (включая Enum, Date и DateTime). На каждом шаге алгоритма кодек берет блок из 64 значений, помещает их в битовую матрицу 64x64, транспонирует ее, отбрасывает неиспользуемые биты значений и возвращает оставшуюся последовательность. Неиспользуемые биты — это биты, которые не различаются у максимального и минимального значений во всей части данных, для которой используется сжатие. Кодеки DoubleDelta и Gorilla используются в Gorilla TSDB как части его алгоритма сжатия. Подход Gorilla эффективен в сценариях, где есть последовательность медленно меняющихся значений с соответствующими временными метками. Временные метки эффективно сжимаются кодеком DoubleDelta, а значения — кодеком Gorilla. Например, чтобы получить таблицу с эффективным хранением, можно создать ее в следующей конфигурации:
CREATE TABLE codec_example
(
    timestamp DateTime CODEC(DoubleDelta),
    slow_values Float32 CODEC(Gorilla)
)
ENGINE = MergeTree()

Кодеки шифрования

Эти кодеки фактически не сжимают данные, а шифруют их на диске. Они доступны только в том случае, если в настройках encryption указан ключ шифрования. Обратите внимание, что шифрование имеет смысл применять только в конце конвейеров кодеков, поскольку зашифрованные данные обычно уже нельзя сколько-либо эффективно сжимать. Кодеки шифрования:

AES_128_GCM_SIV

CODEC('AES-128-GCM-SIV') — Шифрует данные с помощью AES-128 в режиме GCM-SIV, описанном в RFC 8452.

AES-256-GCM-SIV

CODEC('AES-256-GCM-SIV') — шифрует данные с помощью AES-256 в режиме GCM-SIV. Эти кодеки используют фиксированный nonce, поэтому шифрование является детерминированным. Это делает их совместимыми с движками с дедупликацией, такими как ReplicatedMergeTree, но у этого есть слабая сторона: если один и тот же блок данных зашифровать дважды, получившийся шифртекст будет в точности одинаковым, поэтому злоумышленник, имеющий доступ к чтению с диска, сможет увидеть это совпадение (хотя и только факт совпадения, без доступа к содержимому).
Большинство движков, включая семейство “*MergeTree”, создают на диске файлы индекса без применения кодеков. Это означает, что открытый текст появится на диске, если для зашифрованного столбца создан индекс.
Если вы выполняете запрос SELECT, в котором указано конкретное значение в зашифрованном столбце (например, в предложении WHERE), это значение может появиться в system.query_log. Возможно, вам стоит отключить журналирование.
Пример
CREATE TABLE mytable
(
    x String CODEC(AES_128_GCM_SIV)
)
ENGINE = MergeTree ORDER BY x;
Если требуется использовать сжатие, его нужно явно указать. В противном случае к данным будет применяться только шифрование.
Пример
CREATE TABLE mytable
(
    x String CODEC(Delta, LZ4, AES_128_GCM_SIV)
)
ENGINE = MergeTree ORDER BY x;

Временные таблицы

Обратите внимание: временные таблицы не реплицируются. Поэтому нет гарантии, что данные, вставленные во временную таблицу, будут доступны на других репликах. Основной сценарий, в котором временные таблицы могут быть полезны, — выполнение запросов к небольшим внешним датасетам или JOIN с ними в рамках одного сеанса.
ClickHouse поддерживает временные таблицы со следующими характеристиками:
  • Временные таблицы исчезают после завершения сеанса, в том числе при потере соединения.
  • Временная таблица использует движок таблицы Memory, если движок не указан, и может использовать любой движок таблицы, кроме Replicated и KeeperMap.
  • Для временной таблицы нельзя указать БД. Она создаётся вне баз данных.
  • Невозможно создать временную таблицу с помощью распределённого DDL-запроса на всех серверах кластера (с использованием ON CLUSTER): такая таблица существует только в текущем сеансе.
  • Если временная таблица имеет то же имя, что и другая таблица, и в запросе указано имя таблицы без указания БД, будет использована временная таблица.
  • При распределённой обработке запросов временные таблицы с движком Memory, используемые в запросе, передаются на удалённые серверы.
Чтобы создать временную таблицу, используйте следующий синтаксис:
CREATE [OR REPLACE] TEMPORARY TABLE [IF NOT EXISTS] table_name
(
    name1 [type1] [DEFAULT|MATERIALIZED|ALIAS expr1],
    name2 [type2] [DEFAULT|MATERIALIZED|ALIAS expr2],
    ...
) [ENGINE = engine]
В большинстве случаев временные таблицы создаются не вручную, а при использовании внешних данных в запросе или для распределённого (GLOBAL) IN. Подробнее см. в соответствующих разделах Вместо временных таблиц можно использовать таблицы с ENGINE = Memory.

REPLACE TABLE

Оператор REPLACE позволяет атомарно обновить таблицу атомарно.
Этот оператор поддерживается для движков баз данных Atomic и Replicated, которые являются движками баз данных по умолчанию для ClickHouse и ClickHouse Cloud соответственно.
Обычно, если вам нужно удалить часть данных из таблицы, вы можете создать новую таблицу и заполнить её результатом оператора SELECT, который не выбирает нежелательные данные, затем удалить старую таблицу и переименовать новую. Этот подход показан в примере ниже:
CREATE TABLE myNewTable AS myOldTable;

INSERT INTO myNewTable
SELECT * FROM myOldTable 
WHERE CounterID <12345;

DROP TABLE myOldTable;

RENAME TABLE myNewTable TO myOldTable;
Вместо описанного выше подхода можно также использовать REPLACE (при условии, что вы используете движки баз данных по умолчанию), чтобы добиться того же результата:
REPLACE TABLE myOldTable
ENGINE = MergeTree()
ORDER BY CounterID 
AS
SELECT * FROM myOldTable
WHERE CounterID <12345;

Синтаксис

{CREATE [OR REPLACE] | REPLACE} TABLE [db.]table_name
Для этого оператора также применимы все синтаксические формы оператора CREATE. Вызов REPLACE для несуществующей таблицы приведет к ошибке.

Примеры:

Рассмотрим следующую таблицу:
CREATE DATABASE base 
ENGINE = Atomic;

CREATE OR REPLACE TABLE base.t1
(
    n UInt64,
    s String
)
ENGINE = MergeTree
ORDER BY n;

INSERT INTO base.t1 VALUES (1, 'test');

SELECT * FROM base.t1;

┌─n─┬─s────┐
1 │ test │
└───┴──────┘
Мы можем использовать оператор REPLACE, чтобы удалить все данные:
CREATE OR REPLACE TABLE base.t1 
(
    n UInt64,
    s Nullable(String)
)
ENGINE = MergeTree
ORDER BY n;

INSERT INTO base.t1 VALUES (2, null);

SELECT * FROM base.t1;

┌─n─┬─s──┐
2 │ \N │
└───┴────┘
Или можно использовать оператор REPLACE, чтобы изменить структуру таблицы:
REPLACE TABLE base.t1 (n UInt64) 
ENGINE = MergeTree 
ORDER BY n;

INSERT INTO base.t1 VALUES (3);

SELECT * FROM base.t1;

┌─n─┐
3
└───┘

Предложение COMMENT

Комментарий к таблице можно добавить при её создании. Синтаксис
CREATE TABLE [db.]table_name
(
    name1 type1, name2 type2, ...
)
ENGINE = engine
COMMENT 'Comment'
Предложение COMMENT должно быть указано после всех предложений, относящихся к хранилищу, таких как PARTITION BY, ORDER BY и SETTINGS, специфичных для хранилища.После предложения COMMENT будут разбираться только SETTINGS, относящиеся к запросу (например, max_threads и т. д.), а не настройки, связанные с хранилищем.Это означает, что правильный порядок предложений такой:
  • ENGINE
  • предложения хранилища
  • COMMENT
  • настройки запроса (если есть)
Пример
Query
CREATE TABLE t1 (x String) ENGINE = Memory COMMENT 'The temporary table';
SELECT name, comment FROM system.tables WHERE name = 't1';
Response
┌─name─┬─comment─────────────┐
│ t1   │ The temporary table │
└──────┴─────────────────────┘
Последнее изменение 10 июня 2026 г.