Tipo de dado vetorial (ODBC)

Este artigo documenta o tipo de dado vetor SQL conforme implementado pelo Microsoft ODBC Driver para SQL Server a partir da versão 18.6.1.1. Este documento descreve o comportamento do driver Microsoft em relação ao vetor e fornece orientações de utilização, notas específicas da API e excertos de código. Para uma visão geral dos tipos de dados vetoriais, veja Tipo de dados vetorial.

Visão geral

O Microsoft ODBC Driver for SQL Server suporta nativamente o tipo de dado vetorial . As aplicações conseguem armazenar, recuperar e processar eficientemente embeddings numéricos de dimensão fixa comumente usados em cargas de aprendizagem automática e IA. O driver expõe suporte a vetores através de APIs ODBC padrão e tipos de dados C. As aplicações podem interoperar com colunas vetoriais do SQL Server sem alterar os fluxos de trabalho ODBC existentes.

Aplica-se a: Microsoft ODBC Driver para SQL Server 18.6.1.1 e versões posteriores. O suporte para o float16 tipo base requer a versão 18.7.1.1 ou posterior.

O suporte a vetores está desativado por defeito e deve estar explicitamente ativado.

Tipos de elementos base

Uma coluna vetorial declara um tipo de elemento base. O driver suporta ambos os tipos definidos pelo SQL Server.

Tipo de base Indicador de tipo Bytes por elemento no fio Dimensão máxima Versão do controlador
float32 SQL_VECTOR_TYPE_FLOAT32 (0) 4 1,998 18.6.1.1
float16 SQL_VECTOR_TYPE_FLOAT16 (1) 2 3,996 18.7.1.1

float32 é o padrão. Para usar armazenamento de meia precisão, declare a coluna ou parâmetro como VECTOR(<dimensions>, float16). Como um float16 elemento ocupa metade dos bytes do fio, um float16 vetor contém o dobro das dimensões dentro do mesmo limite de carga útil de 8.000 bytes.

Importante

O buffer de aplicação é sempre um array de float (4 bytes por elemento) para ambos os tipos base. O driver converte entre meia precisão no fio e precisão simples no seu buffer. Dimensione cada buffer com sizeof(float), nunca com 2 bytes por elemento, mesmo para uma float16 coluna.

Como float16 tem menos bits de mantissa do que float32, uma viagem de ida e volta através de uma float16 coluna é com perdas. Os valores são arredondados para o valor de meia-precisão representável mais próximo na inserção, e o valor lido de volta é a float32 expansão desse valor arredondado.

No servidor, float16 é necessário o SQL Server 2025 (17.x) com a PREVIEW_FEATURES configuração com escopo da base de dados ativada. Para mais informações, veja Suporte a float de meia precisão no tipo de dado vetorial.

Representação nativa em C

Quando o suporte vetorial está ativado, as colunas vetoriais são trocadas usando uma estrutura C tipada chamada SQL_SS_VECTOR_STRUCT.

    typedef enum
    {
        SQL_VECTOR_TYPE_FLOAT32 = 0,  /* 32-bit floating point */
        SQL_VECTOR_TYPE_FLOAT16 = 1   /* 16-bit floating point */
    } SQLVECTORTYPE;

    typedef struct tagSS_VECTOR_STRUCT {
        SQLSMALLINT   dimension;  /* Number of elements */
        SQLVECTORTYPE type;       /* Element base type indicator */
        union data {
            float* f32;           /* Pointer to float32 data */
            float* f16;           /* Pointer to float16 data */
        } data;
    } SQL_SS_VECTOR_STRUCT;
  • dimension: descreve o número de elementos no vetor
  • type: identifica o tipo de elemento base, SQL_VECTOR_TYPE_FLOAT32 ou SQL_VECTOR_TYPE_FLOAT16
  • data.f32 / data.f16: aponta para o buffer de aplicação que contém valores vetoriais

Ambos os membros da união são declarados como float* e são intercambiáveis, porque o buffer do lado do cliente contém float32 valores para qualquer tipo base. Use o membro que documente a sua intenção.

Ativar suporte a vetores

A vectorTypeSupport palavra-chave cadeia de ligação seleciona o nível de suporte vetorial nativo que a ligação negocia.

Valor Comportamento
off (predefinição) Colunas vetoriais aparecem como varchar(max) contendo arrays JSON.
v1 Suporte vetorial nativo para o float32 tipo base.
v2 Suporte vetorial nativo tanto para o float32 tipo como float16 para o tipo base. Requer o driver versão 18.7.1.1 ou posterior.

Também pode definir o nível depois de alocar a alavanca de ligação e, antes de ligar, com o SQL_COPT_SS_VECTOR_TYPE_SUPPORT atributo pré-conexão de conexão.

  • O driver da Microsoft expõe uma ligação SQL_C_SS_VECTOR C específica do driver e suporta SQL_C_BINARY saída vetorial. Na prática:

    • Quando ativas vectorTypeSupport=v1 ou v2, APIs de recuperação (por exemplo, SQLGetData e SQLBindCol) podem devolver colunas vetoriais como ou SQL_C_SS_VECTORSQL_C_BINARY. SQL_C_SS_VECTOR devolve o vetor numa forma compacta e tipada. SQL_C_BINARY devolve uma carga útil varbinária .

    • Para ligação de entrada ou parâmetros, o driver suporta tanto SQL_C_SS_VECTOR como SQL_C_BINARY. SQL_C_SS_VECTOR fornece uma ligação de entrada tipada e compacta. SQL_C_BINARY é equivalente e portátil. Usa SQL_C_SS_VECTOR quando quiseres que o driver trate a carga útil como um tipo de vetor nativo.

    • Quando vectorTypeSupport=off, as colunas vetoriais aparecem como varchar(max) contendo arrays JSON.

v2 é um superconjunto de v1, pelo que uma ligação negociada em v2 gere float32 colunas exatamente como v1 faz. Enviar um float16 valor numa ligação negociada v1 falha com Requested vector base type is not supported for the negotiated vector version. Usar v2 sempre que a aplicação possa encontrar uma float16 coluna.

As aplicações também devem definir a versão ODBC para ODBC 3.8 antes de usarem tipos específicos de vetor:

    SQLSetEnvAttr(
    hEnv,
    SQL_ATTR_ODBC_VERSION,
    (SQLPOINTER)SQL_OV_ODBC3_80,
    0);

Formatos de ligação suportados

Ligação vetorial nativa

Tipo C: SQL_C_SS_VECTOR

Este formato é recomendado para aplicações críticas de desempenho.

Ligação binária

Tipo C: SQL_C_BINARY

Os vetores são devolvidos usando a mesma disposição que SQL_C_SS_VECTOR. As aplicações podem usar este formato para cenários de interoperabilidade de baixo nível. O buffer de ponteiro de dados pode ser contíguo ou não contíguo ao endereço de memória da estrutura.

Orientação da API ODBC

Esta secção descreve como as APIs ODBC interagem com dados vetoriais do SQL Server, incluindo requisitos de layout de buffers, NULL tratamento e representações de dados suportadas. Todos os comportamentos se aplicam quando vectorTypeSupport está definido como v1 ou v2 e o ambiente está configurado para ODBC 3.8.

Cada fórmula de tamanho de buffer nesta secção usa sizeof(float) por elemento para ambos os tipos de base, porque o buffer do lado do cliente contém float32 sempre valores. Uma float16 coluna altera os bytes no fio, não a disposição do teu buffer.

SQLBindCol

Use SQLBindCol para associar colunas vetoriais em um conjunto de resultados a buffers de aplicação.

  • Chamada típica:
    SQLRETURN SQLBindCol(
      SQLHSTMT       StatementHandle,
      SQLUSMALLINT   ColumnNumber,
      SQLSMALLINT    TargetType,
      SQLPOINTER     TargetValuePtr,
      SQLLEN         BufferLength,
      SQLLEN *       StrLen_or_IndPtr);
  • TargetType: usar SQL_C_SS_VECTOR ou SQL_C_BINARY.

  • TargetValuePtr: apontador para um SQL_SS_VECTOR_STRUCT com um array de floats quando TargetType é SQL_C_SS_VECTOR; caso contrário, aponta para um buffer cujo tamanho é o valor em StrLen_or_IndPtr.

  • BufferLength: sizeof(SQL_SS_VECTOR_STRUCT) + o número de bytes alocados para o buffer da coluna (dimensão * 4).

  • StrLen_or_IndPtr: ponteiro que recebe o comprimento do byte do vetor devolvido (SQL_DESC_OCTET_LENGTH). O seu valor é sizeof(SQL_SS_VECTOR_STRUCT) + o tamanho do array float (dimensão * 4).

Estes tamanhos são os mesmos para uma float16 coluna. O driver expande cada elemento de meia precisão para a float à medida que preenche o teu buffer, e reporta o comprimento expandido.

Expectativas para o layout do buffer

Buffer não contíguo (recomendado)

  • A aplicação aloca um SQL_SS_VECTOR_STRUCT por linha.
  • A aplicação aloca memória para data.f32.
  • O driver preenche os metadados vetoriais e escreve os valores dos elementos no buffer float fornecido.
    SQLLEN numberOfRow = 1000; // set to SQL_ATTR_ROW_ARRAY_SIZE
    SQLULEN columnSize = x; // use SQLDescribeCol or SQLColAttributeW or sizeof(SQL_SS_VECTOR_STRUCT) + (dimension * 4)
    SQL_SS_VECTOR_STRUCT vecBuffer[numberOfRow]
    std::vector<SQLLEN> indicator(numberOfRow, 0);
    for (int i = 0; i < numberOfRow; i++)
    {
        vecBuffer[i].dimension = static_cast<SQLUSMALLINT>((columnSizes[col - 1] - sizeof(SQL_SS_VECTOR_STRUCT)) / 4);
        vecBuffer[i].type = SQL_VECTOR_TYPE_FLOAT32; // or SQL_VECTOR_TYPE_FLOAT16
        vecBuffer[i].data.f32 = (float*)malloc(vecBuffer[i].dimension * sizeof(float));
        if (!vecBuffer[i].data.f32) {
            std::cerr << "Memory allocation failed for vector data." << std::endl;
            return SQL_ERROR;
        }
    }
    SQLBindCol(hStmt, col, SQL_C_SS_VECTOR, vecBuffer, columnSize, indicators.data());

Tampão contíguo

  • A aplicação aloca um único buffer e o ODBC preenche-o em conformidade.
  • A matriz flutuante deve começar imediatamente após o struct.
  • O driver define data.f32 como referência para esta região contígua.
    SQLLEN numberOfRow = 1000; // set to SQL_ATTR_ROW_ARRAY_SIZE
    SQLULEN columnSize = x; // use SQLDescribeCol or SQLColAttributeW or sizeof(SQL_SS_VECTOR_STRUCT) + (dimension * 4)
    std::vector<BYTE> vecBuffer;
    std::vector<SQLLEN> indicator(numberOfRow, 0);
    vecBuffer.resize(numberOfRow * columnSize);
    SQLBindCol(hStmt, col, SQL_C_BINARY, vecBuffer.data(), columnSize, indicators.data());

Gestão de valores NULL para SQLBindCol

Quando o valor da coluna é NULL, o driver define *StrLen_or_IndPtr para SQL_NULL_DATA e não preenche o buffer. Verifique sempre o indicador antes de aceder ao conteúdo vetorial.

Observação

O comportamento de leitura e busca de linhas para colunas vetoriais é descrito em detalhe em SQLFetch e SQLFetchScroll (veja essas referências de API para exemplos de semântica de busca e array-fetch).

SQLGetData

Use SQLGetData para recuperar dados vetoriais de colunas não vinculadas.

  • Chamada típica:
    SQLRETURN SQLGetData(
      SQLHSTMT       StatementHandle,
      SQLUSMALLINT   Col_or_Param_Num,
      SQLSMALLINT    TargetType,
      SQLPOINTER     TargetValuePtr,
      SQLLEN         BufferLength,
      SQLLEN *       StrLen_or_IndPtr);
  • TargetType: usar SQL_C_SS_VECTOR ou SQL_C_BINARY.

  • TargetValuePtr: apontador para um SQL_SS_VECTOR_STRUCT com um array de floats quando TargetType é SQL_C_SS_VECTOR; caso contrário, aponta para um buffer cujo tamanho é o valor em StrLen_or_IndPtr.

  • BufferLength: sizeof(SQL_SS_VECTOR_STRUCT) + o número de bytes alocados para o buffer da coluna (dimensão * 4).

  • StrLen_or_IndPtr: ponteiro que recebe o comprimento do byte do vetor devolvido (SQL_DESC_OCTET_LENGTH). O seu valor é sizeof(SQL_SS_VECTOR_STRUCT) + o tamanho do array float (dimensão * 4).

A recuperação em blocos não é suportada. Tens de recuperar o vetor inteiro numa só chamada.

Exemplo ( vetor nativo):

    SQLLEN dataLen = 0;
    SQL_SS_VECTOR_STRUCT vec = {};
    vec.data.f32 = (float*)malloc(x * sizeof(float)); // x is the dimension
    if (!vec.data.f32) {
        std::cerr << "Memory allocation failed for vector data." << std::endl;
        return SQL_ERROR;
    }
    SQLGetData(hStmt, col, SQL_C_SS_VECTOR, &vec, sizeof(vec) + sizeof(float) * vec.dimension, &dataLen);

Tratamento de NULL em SQLGetData

Quando o valor da coluna é NULL, o driver define *StrLen_or_IndPtr para SQL_NULL_DATA e não preenche o buffer. Verifique sempre o indicador antes de aceder ao conteúdo vetorial.

Observação

O comportamento de leitura e busca de linhas para colunas vetoriais é descrito em detalhe em SQLFetch e SQLFetchScroll (veja essas referências de API para exemplos de semântica de busca e array-fetch).

SQLFetch

Use SQLFetch para buscar a próxima linha e materializar corretamente quaisquer colunas vinculadas SqlVector.

  • Chamada típica:
    SQLRETURN SQLFetch(
     SQLHSTMT     StatementHandle);

Chame SQLFetch no ciclo standard com SqlVector colunas já vinculadas através de SQLBindCol. Ou, usar SQLGetData para recuperar dados para o buffer da aplicação.

Exemplo ( vetor nativo):

    while ((ret = SQLFetch(hStmt)) == SQL_SUCCESS || ret == SQL_SUCCESS_WITH_INFO) {
        // if SQLBindCol was used directly jump to read buffer
        // else use SQLGetData and than read buffer.
        std::cout << "  data: [";
        if (dataLen != SQL_NULL_DATA)
        {
            for (SQLUSMALLINT d = 0; d < vec.dimension; ++d) {
                std::cout << vec.data.f32[d];
                if (d + 1 < vec.dimension) std::cout << ", ";
            }
        }
        std::cout << "]" << std::endl;
    }

SQLFetchScroll

Use SQLFetchScroll para buscar conjuntos de dados de acordo com uma disposição especificada (próximo, anterior, absoluto, relativo, marcador). O driver copia corretamente os dados vetoriais para buffers de aplicação.

  • Chamada típica:
    SQLRETURN SQLFetchScroll(
      SQLHSTMT      StatementHandle,
      SQLSMALLINT   FetchOrientation,
      SQLLEN        FetchOffset);

Exemplo ( vetor nativo):

    // Fetch rows in batches
    while ((ret = SQLFetchScroll(hStmt, SQL_FETCH_NEXT, 0)) != SQL_NO_DATA) {
        for (SQLULEN i = 0; i < numRowsFetched; i++) {
            // In case of Contiguous Buffer
                SQL_SS_VECTOR_STRUCT* vecptr = reinterpret_cast<SQL_SS_VECTOR_STRUCT*>(
                vecBuffer.data() + (i * columnSizes[col - 1]));
                float* floats = reinterpret_cast<float*>(
                reinterpret_cast<char*>(vecptr) + sizeof(SQL_SS_VECTOR_STRUCT)
            );
            // in Case of non-contiguous Buffer
            SQL_SS_VECTOR_STRUCT* vecptr = &vecBuffer[i];
            float* floats = vecptr->data.f32;

            if (indicators[i] != SQL_NULL_DATA)
            {
                for (SQLUSMALLINT d = 0; d < vecptr->dimension; ++d) {
                    std::cout << floats[d];
                    if (d + 1 < vecptr->dimension) std::cout << ", ";
                }
            }
            std::cout << "]" << std::endl;
        }
    }

SQLBindParameter

Use SQLBindParameter para enviar valores vetoriais para o SQL Server.

  • Chamada típica:
    SQLRETURN SQLBindParameter(
        SQLHSTMT        StatementHandle,
        SQLUSMALLINT    ParameterNumber,
        SQLSMALLINT     InputOutputType,
        SQLSMALLINT     ValueType,
        SQLSMALLINT     ParameterType,
        SQLULEN         ColumnSize,
        SQLSMALLINT     DecimalDigits,
        SQLPOINTER      ParameterValuePtr,
        SQLLEN          BufferLength,
        SQLLEN *        StrLen_or_IndPtr);
  • ParameterValuePtr: aponta para um povoado SQL_SS_VECTOR_STRUCT
  • ColumnSize: ignorado para parâmetros de entrada. Para parâmetros de saída e cenários de dados na execução, especifique o tamanho total do vetor: sizeof(SQL_SS_VECTOR_STRUCT) + (tamanho do array flutuante )
  • DecimalDigits: ignorado para parâmetros de entrada. Para parâmetros de saída e cenários de dados na execução, especifique o tipo de base vetorial
  • BufferLength: ≥ sizeof(SQL_SS_VECTOR_STRUCT) + (dimensão * sizeof(float))
  • *StrLen_or_IndPtr: deve conter o mesmo tamanho total

De onde vem o tipo base

O driver lê o tipo de elemento base de um local diferente, dependendo da direção do parâmetro. Errar isto é a causa mais comum ou Invalid vector dimensionProvided buffer length too small/large erros num float16 parâmetro.

Tipo de parâmetro Fonte do tipo base Fonte dimensional
Entrada e entrada/saída O type campo do SQL_SS_VECTOR_STRUCT que passas O dimension corpo da mesma estrutura
Saída pura DecimalDigits Derivado de ColumnSize como (ColumnSize - sizeof(SQL_SS_VECTOR_STRUCT)) / sizeof(float)
Dados na execução DecimalDigits Derivado de ColumnSize, e cruzado com o comprimento passado para SQL_LEN_DATA_AT_EXEC

Para um parâmetro de entrada, BufferLength deve ser igual sizeof(SQL_SS_VECTOR_STRUCT) a + (dimensão * sizeof(float)) exatamente. Um valor maior ou menor falha em vez de ser tolerado.

Exemplo ( vetor nativo, float32):

    float values[3] = {1.0f, 2.0f, 3.0f};
    SQL_SS_VECTOR_STRUCT vec;
    SQLLEN cb;

    vec.dimension = 3;
    vec.type = SQL_VECTOR_TYPE_FLOAT32;
    vec.data.f32 = values;

    cb = sizeof(vec) + sizeof(values);

    SQLBindParameter(
        hStmt, 1, SQL_PARAM_INPUT, SQL_C_SS_VECTOR, SQL_SS_VECTOR, 0, 0, &vec, cb, &cb);

Exemplo ( vetor nativo, float16):

Só o type campo muda. O array de valores mantém-se como float um array e cb é calculado da mesma forma.

    float values[3] = {1.0f, 2.0f, 3.0f};
    SQL_SS_VECTOR_STRUCT vec;
    SQLLEN cb;

    vec.dimension = 3;
    vec.type = SQL_VECTOR_TYPE_FLOAT16;
    vec.data.f16 = values; /* still a float32 array */

    cb = sizeof(vec) + sizeof(values);

    SQLBindParameter(
        hStmt, 1, SQL_PARAM_INPUT, SQL_C_SS_VECTOR, SQL_SS_VECTOR, 0, 0, &vec, cb, &cb);

Exemplo (float16 parâmetro de saída):

Um parâmetro de saída puro não tem estrutura de entrada, pelo que o tipo base é passado e DecimalDigits a dimensão é derivada de ColumnSize.

    SQL_SS_VECTOR_STRUCT vec = {};
    float values[3] = {};
    vec.data.f16 = values;

    SQLULEN columnSize = sizeof(SQL_SS_VECTOR_STRUCT) + 3 * sizeof(float);
    SQLLEN cb = (SQLLEN)columnSize;

    SQLBindParameter(
        hStmt, 1, SQL_PARAM_OUTPUT, SQL_C_SS_VECTOR, SQL_SS_VECTOR,
        columnSize, SQL_VECTOR_TYPE_FLOAT16, &vec, cb, &cb);

Manipulação de NULL para SQLBindParameter

As aplicações podem indicar um NULL vetor usando qualquer uma das abordagens suportadas:

  • Definir *StrLen_or_IndPtr para SQL_NULL_DATA e passar NULL como ParameterValuePtr

  • Forneça um SQL_SS_VECTOR_STRUCT :

    Tipo de conjunto de dimensão definido para o tipo base da coluna data.f32 = NULL

SQLPutData

O driver suporta SQLPutData parâmetros vetoriais com as seguintes restrições:

  • Deve fornecer o vetor completo na primeira chamada.

  • O driver não suporta transmissão vetorial em partes ou incremental.

  • NULL O tratamento segue as mesmas regras que SQLBindParameter.

  • Chamada típica:

    SQLRETURN SQLPutData(
        SQLHSTMT     StatementHandle,
        SQLPOINTER   DataPtr,
        SQLLEN       StrLen_or_Ind);
  • DataPtr: aponta para um povoado SQL_SS_VECTOR_STRUCT
  • StrLen_or_Ind: sizeof(SQL_SS_VECTOR_STRUCT) + (dimensão * sizeof(float))

Exemplo ( vetor nativo):

    std::vector<float> floatArray = { 1.0f, 2.0f, 3.0f };

    SQL_SS_VECTOR_STRUCT vectorValue = {0};
    vectorValue.type = SQL_VECTOR_TYPE_FLOAT32; // or SQL_VECTOR_TYPE_FLOAT16
    vectorValue.dimension = (SQLUSMALLINT)floatArray.size();
    vectorValue.data.f32 = floatArray.data();

    // Tell ODBC this parameter will be supplied at execution time
    SQLLEN cbVectorLen = SQL_LEN_DATA_AT_EXEC(
        (SQLLEN)(sizeof(SQL_SS_VECTOR_STRUCT) + floatArray.size() * sizeof(float))
    );

    // Optional token to identify which parameter needs data
    SQLPOINTER token = (SQLPOINTER)1;

    // Bind as DATA_AT_EXEC: BufferLength is 0, value pointer can be a token
    SQLRETURN rc = SQLBindParameter(hStmt, 1, SQL_PARAM_INPUT, SQL_C_SS_VECTOR, SQL_SS_VECTOR, 0, 0, token, 0, &cbVectorLen);

    if (rc != SQL_SUCCESS && rc != SQL_SUCCESS_WITH_INFO) {
        // handle error
    }

    rc = SQLExecute(hStmt);
    if (rc != SQL_SUCCESS && rc != SQL_SUCCESS_WITH_INFO && rc != SQL_NEED_DATA) {
        // handle error
    }

    SQLPOINTER pParamToken = NULL;
    rc = SQLParamData(hStmt, &pParamToken);

    if (rc == SQL_NEED_DATA) {
        // Provide entire vector in first SQLPutData call (no chunking)
        rc = SQLPutData(
            hStmt,
            (SQLPOINTER)&vectorValue,
            (SQLLEN)(sizeof(SQL_SS_VECTOR_STRUCT) + floatArray.size() * sizeof(float))
        );

        if (rc != SQL_SUCCESS && rc != SQL_SUCCESS_WITH_INFO) {
            // handle error
        }

        // Finalize parameter transfer
        rc = SQLParamData(hStmt, &pParamToken);
    }

Metadados do descritor

Quando ativa o suporte a vetores, o Microsoft ODBC Driver for SQL Server expõe metadados vetoriais através das APIs padrão de descritores ODBC. As aplicações podem usar informação de descritores para descobrir detalhes de esquemas vetoriais, calcular tamanhos de buffer e configurar corretamente ligações para parâmetros e conjuntos de resultados.

Valores de campo descritor para vetor

A tabela seguinte resume os valores dos campos de descrição para colunas e parâmetros vetoriais do SQL Server.

Campo Descritor Valor Description
SQL_DESC_TYPE SQL_SS_VECTOR (-156) Identificador base de tipo de dados SQL
SQL_DESC_CONCISE_TYPE SQL_SS_VECTOR Tipo de dado SQL conciso
SQL_DESC_TYPE_NAME vector Nome do tipo SQL
SQL_DESC_LOCAL_TYPE_NAME vector Nome local do tipo do piloto
SQL_DESC_LENGTH sizeof(SQL_SS_VECTOR_STRUCT) + (dimension * sizeof(float)) Tamanho lógico do valor do vetor
SQL_DESC_OCTET_LENGTH O mesmo que SQL_DESC_LENGTH Tamanho físico em bytes
SQL_DESC_PRECISION O mesmo que SQL_DESC_LENGTH Usado para reportar o tamanho do vetor
SQL_DESC_SCALE SQL_VECTOR_TYPE_FLOAT32 ou SQL_VECTOR_TYPE_FLOAT16 Tipo de elemento base vetorial
SQL_CA_SS_VECTOR_DIMENSION dimension Número de elementos no vetor
SQL_DESC_DISPLAY_SIZE dimension * VECTOR_FLOAT32_TO_CHAR_JSON_MAX_SIZE Comprimento máximo de exibição JSON
SQL_DESC_FIXED_PREC_SCALE SQL_FALSE O vetor não tem precisão/escala fixa
SQL_DESC_NULLABLE SQL_NULLABLE Colunas vetoriais permitem os NULL valores
SQL_DESC_NUM_PREC_RADIX 0 Tipo não numérico
SQL_DESC_SEARCHABLE SQL_PRED_NONE Não utilizável em predicados
SQL_DESC_UNSIGNED SQL_TRUE O tipo de elemento é não assinado
SQL_DESC_AUTO_UNIQUE_VALUE SQL_FALSE Não autoúnico
SQL_DESC_CASE_SENSITIVE SQL_FALSE Não diferencia maiúsculas de minúsculas
SQL_DESC_UPDATABLE SQL_ATTR_READWRITE_UNKNOWN Atualização desconhecida

SQL_DESC_LENGTH, SQL_DESC_OCTET_LENGTH, e SQL_DESC_PRECISION todos descrevem o buffer do lado do cliente, de modo que reportam sizeof(SQL_SS_VECTOR_STRUCT) + (dimensão * sizeof(float)) para uma float16 coluna bem como para um float32 um. Os dois diferem apenas no número de bytes que o SQL Server armazena e transmite.

SQL_DESC_SCALE é o único corpo descritor que distingue os tipos base. Lê-lo é como uma aplicação descobre se uma coluna é float32 ou float16.

SQLColAttribute para dimensão vetorial

A partir da versão 18.7.1.1, SQL_CA_SS_VECTOR_DIMENSION devolve diretamente a contagem de elementos de uma coluna vetorial, de modo que uma aplicação já não precisa de a derivar a partir de um campo de comprimento:

    SQLLEN dimension = 0;
    SQLColAttribute(hStmt, col, SQL_CA_SS_VECTOR_DIMENSION, NULL, 0, NULL, &dimension);

    SQLLEN baseType = 0;
    SQLColAttribute(hStmt, col, SQL_DESC_SCALE, NULL, 0, NULL, &baseType);
    /* baseType is SQL_VECTOR_TYPE_FLOAT32 or SQL_VECTOR_TYPE_FLOAT16 */

Também pode definir SQL_CA_SS_VECTOR_DIMENSION um descritor de aplicação ou o IPD para um parâmetro vetorial. Defini-lo em qualquer outro tipo de parâmetro devolve um erro de campo descritor inválido.

SQLDescribeCol

Quando chamar SQLDescribeCol para uma coluna vetorial :

  • DataType é SQL_SS_VECTOR
  • ColumnSize Jogos SQL_DESC_PRECISION
  • DecimalDigits é o indicador do tipo de elemento base, não uma escala numérica: 0 para float32 e 1 para float16
  • Nullable é SQL_NULLABLE

O tamanho da coluna reportado representa o tamanho da carga útil vetorial nativa: sizeof(SQL_SS_VECTOR_STRUCT) + (dimensão * sizeof(float))

SQLDescribeParam

Quando usa SQLDescribeParam para um parâmetro vetorial :

  • DataType é SQL_SS_VECTOR
  • ColumnSize é igual ao tamanho da carga útil vetorial nativa
  • DecimalDigits é o indicador do tipo de elemento base, não uma escala numérica: 0 para float32 e 1 para float16
  • Nullable é SQL_NULLABLE

Esta informação permite que as aplicações aloquem corretamente os buffers de parâmetros antes de se ligarem.

SQLColAttribute

  • Use SQLColAttribute(hstmt, ColumnNumber, SQL_DESC_OCTET_LENGTH, ...) para obter o comprimento exato do byte da carga útil vetorial. SQL_DESC_LENGTH e SQL_DESC_PRECISION pode ter valores específicos do condutor. Para a contagem de bytes, prefira SQL_DESC_OCTET_LENGTH.

    • NULLtratamento: Quando uma coluna é NULL, (ou o SQLColAttribute usado com StrLen_or_IndPtr), retorna SQLBindColSQL_NULL_DATA. Verifique SQL_NULL_DATA antes de usar os comprimentos ou buffers retornados.

Cópia em massa (BCP)

Pode importar e exportar em massa colunas vetoriais através de ficheiros BCP e da bcp_bind API, tal como outros tipos de dados. Atualmente, a importação e exportação vetorial suporta apenas formato nativo (SQLVECTOR) ou varbinary (SQLBINARY), mas não o formato de caracteres. A conversão entre o tipo de vetor e o tipo de carácter não é suportada.

A cópia em massa honra o mesmo nível de suporte que o resto do condutor. Uma float16 coluna requer uma ligação negociada em vectorTypeSupport=v2. Na utilidade bcp , use -z0 para float32 e -z1 para float16. Para mais informações, consulte a utilidade BCP.

Para mais informações sobre o token de tipo, comprimento padrão do prefixo e comprimento padrão do campo para vetor, consulte Tipo de Armazenamento de Ficheiro, Comprimento de Prefixo e Comprimento de Campo.

bcp_gettypename

Quando se usa bcp_gettypename para obter o nome do tipo SQL do vetor, ele retorna o token do tipo BCP (SQLVECTOR) e "vector".

bcp_bind

Use bcp_bind para inserir variáveis de programa em massa numa coluna vetorial .

Chamada típica:

RETCODE bcp_bind (
        HDBC hdbc,
        LPCBYTE pData,
        INT cbIndicator,
        DBINT cbData,
        LPCBYTE pTerm,
        INT cbTerm,
        INT eDataType,
        INT idxServerCol);
  • pData: se cbIndicator for zero, contém um apontador para SQL_SS_VECTOR_STRUCT dados, com dados de array flutuante dentro dele (vectorStruct.data.f32 campo). Se cbIndicator for diferente de zero, o indicador aparece na memória diretamente antes dos dados. Assim, pData aponta para um buffer que primeiro tem cbIndicator bytes de indicador de comprimento, seguido da estrutura vetorial.
  • cbData: se fornecida, deve ter valor exatamente igual a - sizeof(SQL_SS_VECTOR_STRUCT) + (sizeof(float) * dimensão). Caso contrário, ocorre um erro. Isto é igual para ambos os tipos de base, porque o buffer bound mantém float32 valores em ambos os sentidos.
  • eDataType: SQLVECTOR ou SQLBINARY

Defina o type campo da estrutura para o tipo base da coluna. Para uma float16 coluna, o driver converte o array limitado float32 para meia precisão enquanto constrói a carga útil do fio, pelo que um ficheiro de dados escrito em formato nativo contém dois bytes por elemento.

Quando importas dados para uma coluna vetorial através de bcp_bind, define eDataType para SQLVECTOR ou SQLBINARY. Em ambos os casos, deve fornecer dados na forma de SQL_SS_VECTOR_STRUCT.

Solução de problemas e dicas

  • Se SQLGetTypeInfo não listar VECTOR, volta a armazenar vetores como varchar.
  • Requested vector base type is not supported for the negotiated vector version. significa que um float16 valor foi usado numa ligação negociada em vectorTypeSupport=v1. Reconecte-se com v2.
  • Provided buffer length too small/large. significa BufferLength que não correspondia sizeof(SQL_SS_VECTOR_STRUCT) exatamente a + (dimensão* sizeof(float)). Verifique se o buffer tem um tamanho com sizeof(float) em vez de dois bytes por elemento, mesmo para uma float16 coluna.
  • Invalid vector dimension significa que a dimensão é zero, ou excede o máximo para o tipo base: 1.998 para float32 e 3.996 para float16.
  • Invalid vector base type significa que o type corpo detinha um valor diferente de SQL_VECTOR_TYPE_FLOAT32 ou SQL_VECTOR_TYPE_FLOAT16. Uma estrutura inicializada a zero tem por defeito .float32
  • Se uma float16 coluna for reportada como varchar(max) contendo um array JSON, o servidor não tem a PREVIEW_FEATURES configuração com escopo da base de dados ativada, nem a ligação negociada um nível inferior a v2.