You need to enable JavaScript to run this app.
导航
通过 Python API 使用向量检索
最近更新时间:2025.05.22 14:27:20首次发布时间:2024.03.14 11:22:40
我的收藏
有用
有用
无用
无用

本文介绍了如何通过 Python API 连接至 ByteHouse 并使用向量检索。

前提条件
  • 请确保您已安装 Python 工具,且版本为 Python 3.8 或更高版本。
  • 请确保您使用的 ByteHouse 为 v2.6 及以上版本。您可登录 ByteHouse 控制台,进入集群列表,单击目标集群,在基础信息页面中查看您使用的引擎版本。
    Image
  • 请确保您已开启向量检索服务
  • 获取 ByteHouse 连接信息,详情请参见获取集群连接信息

通过 HTTP 连接

步骤 1:建立连接

from clickhouse_connect import get_client
client = get_client(host="server", # server ip
                         port=8123,  # server http port
                         user="bytehouse", # user
                         password="password", # password
                         compress='zstd', # compress method, zstd recommanded
                         send_receive_timeout=1000) # connect timeout

参数说明

参数项

是否必填

配置说明

host

服务器 IP 地址或域名。配置为 ByteHouse 的公网连接域名,您可以在 ByteHouse 控制台的 集群管理 > 集群列表 > 集群 > 基本信息 中查看对应信息。详情请参见集群连接地址

port

配置为 8123。

user

固定配置为 bytehouse。

password

在首次通过 IAM 账号密码登录火山引擎后,系统会自动生成 ByteHouse 初始服务密码。您可联系管理员获取。如果密码丢失或遗忘,可重置连接密码

compress

定义数据压缩方式,支持设置为 zstd、lz4、False。

  • zstd:推荐设置,压缩率高,CPU 开销适中。
  • lz4:压缩速度快,但压缩率低于 ZSTD。
  • False:禁用压缩。禁用后,传输大结果集时可能影响性能。

send_receive_timeout

设置单次请求的超时时间,单位为秒。

步骤 2:建表

  1. 定义建表 schema。

    schema = f"""\
                    CREATE TABLE IF NOT EXISTS {database}.{table}(
                        id UInt64,
                        embedding Array(Float32),
                        CONSTRAINT cons_vec_len CHECK length(embedding) = {dim},
                        INDEX vec_idx embedding TYPE HNSW('METRIC={metric.upper()}, DIM={dim}')
                    ) ENGINE = {engine} ORDER BY id\
                    """
    

    参数说明

    参数项

    是否必填

    配置说明

    embedding Array

    向量字段,存储浮点数数组。

    CONSTRAINT cons_vec_len CHECK length(embedding)

    定义向量的维度值为 {dim},用于确保数据一致性,避免因维度不匹配导致索引异常。

    INDEX vec_idx embedding

    声明要创建的索引及索引的列名。示例中,

    • vec_idx 为索引的名称,支持自定义。
    • embedding 为要建立索引的列名,通常使用存储向量的数组字段。

    TYPE HNSW

    定义使用的索引算法,支持设置为 HNSW、HNSW_SQ、FLAT、IVF_FLAT、IVF_PQ、IVF_SQ。
    索引支持设置参数,部分参数定义如下,其他可配置的参数可参考索引参数

    • METRIC:距离度量方式,支持设置为 L2、COSINE。
    • DIM:向量维度,必须与 embedding 字段的实际维度数值一致。

    ENGINE

    数据库引擎,可设置为 MergeTree、HaMergeTree 或 HaUniqueMergeTree。

    ORDER BY id

    id 字段排序数据,加速基于 id 的查询。

  2. 执行建表语句。

    client.command(schema) 
    

步骤 3:插入向量

  1. 数据预处理。

    #  embeddings(list[list[float]])指向量列表
    #  ids(list[int])指向量对应的唯一标识
    data = zip(ids, embeddings)
    values = [list(elem) for elem in data]
    

    参数说明

    参数项

    是否必填

    配置说明

    data = zip(ids, embeddings)

    数据预处理,将 idsembeddings 两个列表按元素位置配对,合并为元组迭代器。

    values = [list(elem) for elem in data]

    数据预处理,将每个元组转换为列表,最终得到列表的列表。

  2. 插入数据。

    client.insert(f'{database}.{table}', values, column_names=['id', 'embedding'],
          column_type_names=['UInt64', 'Array(Float32)'])
    

    参数说明

    参数项

    是否必填

    配置说明

    client.insert

    定义需要插入的数据。

    f'{database}.{table}'

    定义目标表名。

    values

    二维列表,表示多行数据。每行数据的顺序必须与 column_names 一致。

    column_names

    指定列名的顺序。

    column_type_names

    指定列的类型。

步骤 4:查询

  1. 构建查询语句。

    # query: list[float] 
    q_str = f"""
            SELECT id
            FROM {database}.{collection}
            ORDER BY {metric}Distance(embedding, {str(query)}) 
            LIMIT {k}
            settings enable_new_ann=1, hnsw_ef_s={search_param["ef"]}
            """
    

    参数说明

    参数项

    是否必填

    配置说明

    {database}.{collection}

    指定目标表名。

    {metric}Distance

    定义距离函数,支持设置为 L2DistanceCosineDistance。需与建表时使用的函数保持一致。
    {str(query)} :将查询向量转换为列表字符串(如 [0.1, 0.2, ...])。

    LIMIT {k}

    返回最相似的前 k 条记录。

    settings

    示例中配置的 settings 参数说明如下,其他可配置的 settings 参数详见Settings 参数

    • enable_new_ann:需设置为 1,表示启用新的向量近似搜索(ANN)引擎。
    • hnsw_ef_s:表示在搜索时使用的 ef 值,用于控制搜索范围,值越大,搜索越精确,但性能越低。
  2. 执行查询。

    results = client.query(q_str)  
    
  3. 解析结果并提取结果 ID。

    result_ids = [int(id) for id in results.result_columns[0]] 
    

通过 TCP 连接

步骤 1:建立连接

from clickhouse_driver import Client
client = Client(host="server", # server ip
                         port=9000,  # server tcp port
                         user="test", # user
                         password="password", # password
                         connect_timeout=3000,
                         send_receive_timeout=3000) # connect timeout

参数说明

参数项

是否必填

配置说明

host

服务器 IP 地址或域名。配置为 ByteHouse 的公网连接域名,您可以在 ByteHouse 控制台的 集群管理 > 集群列表 > 集群 > 基本信息 中查看对应信息。详情请参见集群连接地址

port

配置为 9000。

user

固定配置为 bytehouse。

password

在首次通过 IAM 账号密码登录火山引擎后,系统会自动生成 ByteHouse 初始服务密码。您可联系管理员获取。如果密码丢失或遗忘,可重置连接密码

compress

定义数据压缩方式,支持设置为 zstd、lz4、False。

  • zstd:推荐设置,压缩率高,CPU 开销适中。
  • lz4:压缩速度快,但压缩率低于 ZSTD。
  • False:禁用压缩。禁用后,传输大结果集时可能影响性能。

send_receive_timeout

设置单次请求的超时时间,单位为秒。

步骤 2:建表

  1. 定义建表 schema。

    schema = f"""\
                    CREATE TABLE IF NOT EXISTS {database}.{table}(
                        id UInt64,
                        embedding Array(Float32),
                        CONSTRAINT cons_vec_len CHECK length(embedding) = {dim},
                        INDEX vec_idx embedding TYPE HNSW('METRIC={metric.upper()}, DIM={dim}')
                    ) ENGINE = {engine} ORDER BY id\
                    """
    

    参数说明

    参数项

    是否必填

    配置说明

    {database}.{table}

    自定义数据库和表名。

    embedding Array

    向量字段,存储浮点数数组。

    CONSTRAINT cons_vec_len CHECK length(embedding)

    定义向量的维度值为 {dim},用于确保数据一致性,避免因维度不匹配导致索引异常。

    INDEX vec_idx embedding

    声明要创建的索引及索引的列名。示例中,

    • vec_idx 为索引的名称,支持自定义。
    • embedding 为要建立索引的列名,通常使用存储向量的数组字段。

    TYPE HNSW

    定义使用的索引算法,支持设置为 HNSW、HNSW_SQ、FLAT、IVF_FLAT、IVF_PQ、IVF_SQ。
    索引支持设置参数,部分参数定义如下,其他可配置的参数可参考索引参数

    • METRIC:距离度量方式,支持设置为 L2、COSINE。
    • DIM:向量维度,必须与 embedding 字段的实际维度数值一致。

    ENGINE

    数据库引擎,可设置为 MergeTree、HaMergeTree 或 HaUniqueMergeTree。

    ORDER BY id

    id 字段排序数据,加速基于 id 的查询。

  2. 执行建表语句。

    client.execute(schema)
    

步骤 3:插入向量

  1. 数据预处理。

    #  embeddings(list[list[float]]): list of embeddings
    #  ids(list[int]): list of ids
    data = zip(ids, embeddings)
    values = [list(elem) for elem in data]
    

    参数说明

    参数项

    是否必填

    配置说明

    data = zip(ids, embeddings)

    数据预处理步骤,将 idsembeddings 两个列表按元素位置配对,合并为元组迭代器。

    values = [list(elem) for elem in data]

    数据预处理步骤,将每个元组转换为列表,最终得到列表的列表。

  2. 插入数据。

    client.execute(f'INSERT INTO {database}.{table} (id, embedding) VALUES', values)
    

    参数说明

    参数项

    是否必填

    配置说明

    client.execute()

    定义需要插入的数据。

    f'INSERT INTO {database}.{table} (id, embedding) VALUES'

    定义目标表名及需要插入的字段及其值。

    • {database}.{table}:指定目标数据库和表名。
    • id, embedding:指定列名列表。
    • VALUES:待插入的数据。

    values

    二维列表,表示多行数据。每行数据的顺序必须与 column_names 一致。

步骤 4:查询

  1. 构建查询语句。

    # query: list[float]
    q_str = f"""
            SELECT id
            FROM {database}.{collection}
            ORDER BY {metric}Distance(embedding, {str(query)}) 
            LIMIT {k}
            settings enable_new_ann=1, hnsw_ef_s={search_param["ef"]}
            """
    

    参数说明

    参数项

    是否必填

    配置说明

    {database}.{collection}

    指定目标表名。

    {metric}Distance

    定义距离函数,支持设置为 L2DistanceCosineDistance。需与建表时使用的函数保持一致。
    {str(query)} :将查询向量转换为列表字符串(如 [0.1, 0.2, ...])。

    LIMIT {k}

    返回最相似的前 k 条记录。

    settings

    示例中配置的 settings 参数说明如下,其他可配置的 settings 参数详见Settings 参数

    • enable_new_ann:需设置为 1,表示启用新的向量近似搜索(ANN)引擎。
    • hnsw_ef_s:表示在搜索时使用的 ef 值,用于控制搜索范围,值越大,搜索越精确,但性能越低。
  2. 执行查询。

    results = client.query(q_str) 
    
  3. 解析结果并提取结果 ID。

    result_ids = [int(i) for (i,) in results]