利用DeepSeek解決kdb+x進行tpch測試的幾個問題及使用感受

上文其實沒有成功運行tpch的22個標準查詢中的任何一個,因為DeepSeek原始給出的導入語句有錯,有一些表沒有導入。

1.解決類型及長度問題導致的插入tbl文件到內存表失敗。
kdb+x的Reference card()提到的基本數據類型如下:

Basic datatypes
n   c   name      sz  literal            null inf SQL       Java      .Net
------------------------------------------------------------------------------------
0   *   list
1   b   boolean   1   0b                                    Boolean   boolean
2   g   guid      16                     0Ng                UUID      GUID
4   x   byte      1   0x00                                  Byte      byte
5   h   short     2   0h                 0Nh  0Wh smallint  Short     int16
6   i   int       4   0i                 0Ni  0Wi int       Integer   int32
7   j   long      8   0j                 0Nj  0Wj bigint    Long      int640                  0N   0W
8   e   real      4   0e                 0Ne  0We real      Float     single
9   f   float     8   0.0                0n   0w  float     Double    double0f                 0Nf
10  c   char      1   " "                " "                Character char
11  s   symbol        `                  `        varchar
12  p   timestamp 8   dateDtimespan      0Np  0Wp           Timestamp DateTime (RW)
13  m   month     4   2000.01m           0Nm
14  d   date      4   2000.01.01         0Nd  0Wd date      Date
15  z   datetime  8   dateTtime          0Nz  0wz timestamp Timestamp DateTime (RO)
16  n   timespan  8   00:00:00.000000000 0Nn  0Wn           Timespan  TimeSpan
17  u   minute    4   00:00              0Nu  0Wu
18  v   second    4   00:00:00           0Nv  0Wv
19  t   time      4   00:00:00.000       0Nt  0Wt time      Time      TimeSpanColumns:
n    short int returned by type and used for Cast, e.g. 9h$3
c    character used lower-case for Cast and upper-case for Tok and Load CSV
sz   size in bytes
inf  infinity (no math on temporal types); 0Wh is 32767hRO: read only; RW: read-write

tpch數據庫常用的也就整型、浮點、日期、字符、變長字符串這幾種,在導入時指定的類型要與數據文件中的數據匹配,就沒有問題。
導入同時建表的語法是:

表名:字段列表(用反引號前綴表示變長字符串,無需分隔符),xcol("大寫的各列數據類型列表"; enlist "數據文件的列分隔符" ) 0: 反引號冒號開頭的文件路徑

比如orders表, 它的SQL建表語句如下:

CREATE TABLE ORDERS  ( 
O_ORDERKEY       INTEGER ,
O_CUSTKEY        INTEGER ,
O_ORDERSTATUS    CHAR(1) ,
O_TOTALPRICE     DECIMAL(15,2) ,
O_ORDERDATE      DATE ,
O_ORDERPRIORITY  CHAR(15) ,  
O_CLERK          CHAR(15) , 
O_SHIPPRIORITY   INTEGER ,
O_COMMENT        VARCHAR(79) );

對應導入語句就是

\t orders:`o_orderkey`o_custkey`o_orderstatus`o_totalprice`o_orderdate`o_orderpriority`o_clerk`o_shippriority`o_comment xcol ("IISFDSSIS"; enlist "|") 0: `:/mnt/c/d/tpch/orders.tbl;

同理,lineitem表導入語句就是

\t lineitem:`l_orderkey`l_partkey`l_suppkey`l_linenumber`l_quantity`l_extendedprice`l_discount`l_tax`l_returnflag`l_linestatus`l_shipdate`l_commitdate`l_receiptdate`l_shipinstruct`l_shipmode`l_comment xcol ("IIIIFFFFCCDDDSSS"; enlist "|") 0: `:/mnt/c/d/tpch/lineitem.tbl;

整數類型有3種,j表示64位,i表示32位,h表示16位二進制。浮點有兩種,e表示單精度、f表示雙精度。

2.解決將內存表保存到持久存儲的數據庫的嵌套目錄問題
前文提到

1. 創建數據庫目錄
// 創建數據庫目錄(如果不存在)
system "mkdir -p tpch_db";2. 保存表到磁盤
// 保存 region 表
`:tpch_db/region/ set .Q.en[`:tpch_db] region;
輸入//
退出kdb
3. 下次啟動時加載
// 啟動 kdb+ 并加載數據庫
q tpch_db

但是,此時如果繼續用上述命令保存其他表,就會產生數據庫的嵌套目錄問題,具體表現是在tpch_db目錄下又建立了tpch_db目錄,其他表被保存到更深的目錄中,并且退出重新進入kdb, 用tables[]命令看不到后加的表。
DeepSeek給出的方法不完全對。他說要

// 更新 .d 文件(包含所有表名)
(`:tpch_db/.d) set `customer`part`nation;

但其實,只要在操作系統把深層目錄移動到父目錄就可以識別了。
關鍵是要修改保存表的路徑,不能再包含tpch_db,比如導入supplier, 這么寫

\t `:supplier/ set .Q.en[`:tpch_db] supplier;

就能使supplier保存在當前數據庫,也就是首層tpch_db目錄下。

3.部分解決存儲分區表問題

上文提到,導入單個大表非常慢,希望分區可以解決,但是DeepSeek給出的原始導入分區語句有誤,報錯如下

\t {date: first x`o_orderdate; `:orders/,string date/ set .Q.en[`:tpch_db] x; } each {select from ordersByDate where o_orderdate=x} each distinct ordersByDate`o_orderdate;
'[0]  \t {date: first x`o_orderdate; `:orders/,string date/ set .Q.en[`:tpch_db] x; } each {select from ordersByDate where o_orderdate=x} each distinct ordersByDate`o_orderdate;^

把報錯位置提供給DeepSeek后,他給出了正確的語句

\t {date: first x`o_orderdate; path: `$":orders/",string date; path set .Q.en[`:tpch_db] x;} each {select from ordersByDate where o_orderdate=x} each distinct ordersByDate`o_orderdate;

語法雖然對了,可以執行,但速度很慢,orders 2分鐘才生成了200多個256K的小文件,64MB,原始數據有1.7GB,怎么加速?DeepSeek給出了多個方法

要加速 kdb+/q 中將大容量 orders 表按日期分區存儲到磁盤的過程,可以綜合采用以下優化策略。您的原始數據 1.7GB 生成過多小文件(200+個 256KB)導致 I/O 瓶頸,以下是針對性解決方案:


1. 并行化處理(核心優化)

使用 peach 多線程并行寫入,需先設置從線程數:

// 啟動 q 時啟用 4 個從線程(根據 CPU 核心數調整)
q -s 4// 在腳本中并行分區保存
{[date]data: select from ordersByDate where o_orderdate=date;path: `$":tpch_db/orders/",string date;path set .Q.en[`:tpch_db] data;} peach distinct ordersByDate`o_orderdate;

效果:寫入速度可提升 3-5 倍(取決于磁盤 I/O 并行能力)。


2. 批量寫入(減少小文件)

合并相鄰日期的數據,減少文件數量:

// 按月份分組寫入(替代按天)
months: `month$distinct ordersByDate`o_orderdate;
{[m]dates: where `month$ordersByDate`o_orderdate=m;path: `$":tpch_db/orders/",string m;path set .Q.en[`:tpch_db] select from ordersByDate where `month$o_orderdate=m;} each months;

優勢:1.7GB 數據可能從 200+ 文件減少到 20-30 個月份文件,顯著降低 I/O 壓力。


3. 啟用壓縮(減少磁盤寫入量)

// 設置高壓縮比(壓縮級別 17,塊大小 128KB)
.z.zd:17 2 7;  // 格式:[compressionLevel; log2BlockSize; algorithm]// 壓縮后再寫入
path set .Q.en[`:tpch_db] data;

效果:文本數據通常可壓縮至原始大小的 30%,寫入量從 1.7GB → ~500MB。


4. 直接原始數據分區(跳過內存排序)

orders.tbl 文件已按日期排序,直接流式處理避免全量加載內存:

// 按日期流式讀取并分區保存
.Q.fs[{ [x]date: first x`o_orderdate;path: `$":tpch_db/orders/",string date;path set .Q.en[`:tpch_db] x;}] (`:orders.tbl; "JJFSDSSIS"; "|");  // 指定數據類型和分隔符

優勢:內存占用極低,適合超大文件。


5. 文件系統優化

調整掛載參數(Linux)
# 掛載時啟用寫入緩存和更大IO隊列
mount -o remount,noatime,discard,data=writeback /mnt/tpch_db
預分配文件空間
// 在 q 中預創建空文件(減少碎片)
{[date;sizeMB]path: `$":tpch_db/orders/",string date;h: hopen path;hclose h;system truncate -s ",(string sizeMB),"M ",1_string path;}[;256] each distinct ordersByDate`o_orderdate;  // 預分配256MB/文件

6. 完整優化腳本示例

// 初始化環境
system "mkdir -p tpch_db/orders";
.z.zd:17 2 7;  // 啟用壓縮
\l tpch_db     // 加載已有數據庫// 方法1:并行按月分區(推薦)
months: distinct `month$ordersByDate`o_orderdate;
{[m]path: `$":tpch_db/orders/",string m;path set .Q.en[`:tpch_db] select from ordersByDate where `month$o_orderdate=m;} peach months;// 方法2:流式處理原始文件(替代方案)
.Q.fs[{ [x]m: `month$first x`o_orderdate;path: `$":tpch_db/orders/",string m;path upsert .Q.en[`:tpch_db] x;}] (`:orders.tbl; "JJFSDSSIS"; "|");

性能對比

方法耗時(1.7GB數據)文件數量內存占用
原始單線程按天~120秒200+
并行按月(4線程)~25秒12-24
流式處理~40秒自動合并極低

進一步建議

  1. 監控磁盤 I/O
    iostat -xmt 1  # 觀察磁盤利用率
    
  2. 使用更快的存儲
    • 臨時寫入到 SSD(如 /dev/shm),完成后移動到 HDD
  3. 后期維護
    .Q.gc[];  // 定期回收內存
    

通過組合 并行化 + 批量合并 + 壓縮,您應該能將總寫入時間從 2 分鐘縮短到 20-30 秒。

經過試驗,多個進程并行有效,partsupp.tbl有1.1GB,25秒完成導入,14秒寫入數據庫

q tpch_db -s 4
\t partsupp:`ps_partkey`ps_suppkey`ps_availqty`ps_supplycost`ps_comment xcol ("IIIFS"; enlist "|") 0: `:/mnt/c/d/tpch/partsupp.tbl;
24704
\t `:partsupp/ set .Q.en[`:tpch_db] partsupp;
13716

按月份分區的語法還是不對,放棄分區,存成單獨文件,還挺快的。

\t {[m] monthData: select from ordersByDate where `month$o_orderdate = m; path: `$":orders/",string m; path set .Q.en[`:tpch_db] monthData;  } each months;
'type[10] {[m] monthData: select from ordersByDate where `month$o_orderdate = m; path: `$":orders/",string m; path set .Q.en[`:tpch_db] monthData;  }^
\t `:orders/ set .Q.en[`:tpch_db] orders;
14835

但并行也更占內存,原來單進程能導入的最大表,7.3GB的lineitem.tbl, 設為多進程,并行度4個或2個,都報錯失敗,也可能由于kdb已經加載了其他表,占用了很多內存。

\t lineitem:`l_orderkey`l_partkey`l_suppkey`l_linenumber`l_quantity`l_extendedprice`l_discount`l_tax`l_returnflag`l_linestatus`l_shipdate`l_commitdate`l_receiptdate`l_shipinstruct`l_shipmode`l_comment xcol ("IIIIFFFFCCDDDSSS"; enlist "|") 0: `:/mnt/c/d/tpch/lineitem.tbl;
rlwrap: error: read error on master pty: Input/output error

4.未能解決真實的tpch查詢執行失敗問題
雖然只導入了8張表,但有些tpch查詢是用不到lineitem表的。其中Q3就是,將sql語句的換行全都刪除,然后執行,結果還是被殺進程了。

s)SELECT s_acctbal,s_name,n_name,p_partkey,p_mfgr,s_address,s_phone,s_comment FROM part,supplier,partsupp,nation,region WHERE p_partkey = ps_partkey AND s_suppkey = ps_suppkey AND p_size = 15 AND p_type LIKE '%BRASS' AND s_nationkey = n_nationkey AND n_regionkey = r_regionkey AND r_name = 'EUROPE' AND ps_supplycost = ( SELECT min(ps_supplycost) FROM partsupp,supplier,nation,region WHERE p_partkey = ps_partkey AND s_suppkey = ps_suppkey AND s_nationkey = n_nationkey AND n_regionkey = r_regionkey AND r_name = 'EUROPE') ORDER BY s_acctbal DESC,n_name,s_name,p_partkey LIMIT 10
Killed

而同樣的機器duckdb執行sf=10的q3只要1.5秒,看來kdb對tpch測試不擅長,它的主要優勢還是時間序列分析。而且學習曲線陡峭,若沒有AI輔助,自己查詢文檔資料,連這些都很難短時間做到。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/diannao/92959.shtml
繁體地址,請注明出處:http://hk.pswp.cn/diannao/92959.shtml
英文地址,請注明出處:http://en.pswp.cn/diannao/92959.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

SGLang 核心技術詳解

SGLang 作為一個高性能的 LLM 服務框架,通過一系列先進的優化技術實現了卓越的推理性能。下面詳細解釋其核心功能組件: 1. RadixAttention 用于前綴緩存 核心概念 RadixAttention 是 SGLang 獨創的前綴緩存機制,基于 Radix Tree(基…

精密全波整流電路(四)

精密全波整流電路(四) 背景說明 [[精密半波整流電路|半波整流]]雖然能實現交直流信號的轉換,但是半波整流只能保留信號半個周期的能量,導致信號能量的利用率不高。 因此,在一些場合需要使用到全波整流電路。 同樣的&…

深入解讀Prometheus 2.33 Series Chunks壓縮特性:原理與實踐

深入解讀Prometheus 2.33 Series Chunks壓縮特性:原理與實踐 隨著監控指標規模不斷增長,Prometheus的本地TSDB存儲壓力日益增大。為提升存儲效率,Prometheus 2.33引入了Series Chunks壓縮特性,對時間序列數據在寫入和存儲時進行深…

SpringBoot整合Liquibase提升數據庫變更的可控性、安全性、自動化程度(最詳細)

為什么要使用liquibase?- 團隊協作與版本管理- 當多人(或多個小組)并行開發、對同一數據庫結構進行變更時,如果僅靠手寫 SQL 腳本,很 容易產生沖突或漏掉某些變更。- Liquibase 將所有 DDL/DML 操作以“changeset”形式納入源碼管…

數據寫入因為漢字引發的異常

spark 數據寫hive表,發生 查詢分區異常問題 異常: 25107124 19 26.49 ERROR Hive: MelaException(message.Exception thrown when execuling quey. S ELECT DISTINCT ‘org apache.hadop.hive melastore .modelMpartion As"NUCLEUS TYPE,AONCREATE TIME,AO.LAST ACCE…

Springboot項目實現將文件上傳到阿里云

Springboot項目實現將文件上傳到阿里云 一、概述二、具體步驟 2.1引入阿里云工具 首先先建utils包,然后引入AliOSSUtils類,如下: package com.hechixueyuan.forestfiredetectionsystem.utils;import com.aliyun.oss.OSS; import com.aliyun.o…

如何理解 TCP 是字節流協議?詳解

文章目錄一、面向字節流二、粘包問題應用層如何解決粘包問題?一、面向字節流 使用 TCP socket 進行網絡編程,Linux 內核會給每個 socket 都分配一個發送緩沖區和一個接收緩沖區 由于緩沖區的存在, TCP 讀寫不需要一一匹配,例如:…

面試問題總結——關于OpenCV(二)

最近小組在面試視覺算法工程師,順便整理了一波關于OpenCV的面試題目。 有些知識點也不深入,對于寫的不對的地方,歡迎指正。 目錄 20.像素梯度如何計算? 21.關于開運算和閉運算的理解 22.開運算和閉運算有什么優缺點? 23.圖像插值有哪些? 24.圖像金字塔的原理 25.邊緣檢測…

目標導向的強化學習:問題定義與 HER 算法詳解—強化學習(19)

目錄 1、目標導向的強化學習:問題定義 1.1、 核心要素與符號定義 1.2、 核心問題:稀疏獎勵困境 1.3、 學習目標 2、HER(Hindsight Experience Replay)算法 2.1、 HER 的核心邏輯 2.2、 算法步驟(結合 DDPG 舉例…

2025 XYD Summer Camp 7.21 智靈班分班考 · Day1

智靈班分班考 Day1 時間線 8:00 在濱蘭實驗的遠古機房中的一個鍵盤手感爆炸的電腦上開考。開 T1,推了推發現可以 segment tree 優化 dp,由于按空格需要很大的力氣導致馬蜂被迫改變。后來忍不住了頂著疼痛按空格。8:30 過了樣例,但是沒有大樣…

基于多種主題分析、關鍵詞提取算法的設計與實現【TF-IDF算法、LDA、NMF分解、BERT主題模型】

文章目錄有需要本項目的代碼或文檔以及全部資源,或者部署調試可以私信博主一、項目背景二、研究目標與意義三、數據獲取與處理四、文本分析與主題建模方法1. 傳統方法探索2. 主題模型比較與優化3. 深度語義建模與聚類五、研究成果與應用價值六、總結與展望總結每文一…

MDC(Mapped Diagnostic Context) 的核心介紹與使用教程

關于日志框架中 MDC(Mapped Diagnostic Context) 的核心介紹與使用教程,結合其在分布式系統中的實際應用場景,分模塊說明: 一、MDC 簡介 MDC(映射診斷上下文) 是 SLF4J/Logback 提供的一種線程…

Linux隨記(二十一)

一、highgo切換leader,follow - 隨記 【待寫】二、highgo的etcd未授權訪問 - 隨記 【待寫】三、highgo的etcd未授權訪問 - 隨記 【待寫】3.2、etcd的metric未授權訪問 - 隨記 【待寫】四、安裝Elasticsearch 7.17.29 和 Elasticsearch 未授權訪問【原理掃描】…

Java環境配置之各類組件下載安裝教程整理(jdk、idea、git、maven、mysql、redis)

Java環境配置之各類組件下載安裝教程整理(jdk、idea、git、maven、mysql、redis)1.[安裝配置jdk8]2.[安裝配置idea]3.[安裝配置git]4.[安裝配置maven]5.[安裝配置postman]6.[安裝配置redis和可視化工具]7.[安裝配置mysql和可視化工具]8.[安裝配置docker]…

配置https ssl證書生成

1.可用openssl生成私鑰和自簽名證書 安裝opensslsudo yum install openssl -y 2.生成ssl證書 365天期限sudo openssl req -x509 -nodes -days 365 -newkey rsa:2048 \-keyout /etc/ssl/private/nginx-selfsigned.key \-out /etc/ssl/certs/nginx-selfsigned.crt3、按照提示編…

編程語言Java——核心技術篇(四)集合類詳解

言不信者行不果,行不敏者言多滯. 目錄 4. 集合類 4.1 集合類概述 4.1.1 集合框架遵循原則 4.1.2 集合框架體系 4.2 核心接口和實現類解析 4.2.1 Collection 接口體系 4.2.1.1 Collection 接口核心定義 4.2.1.2 List接口詳解 4.2.1.3 Set 接口詳解 4.2.1.4…

GaussDB 數據庫架構師(八) 等待事件(1)-概述

1、等待事件概述 等待事件:指當數據庫會話(session)因資源競爭或依賴無法繼續執行時,進入"等待"狀態,此時產生的性能事件即等待事件。 2、等待事件本質 性能瓶頸的信號燈,反映CPU,I/O、鎖、網絡等關鍵資源的阻塞情況。…

五分鐘系列-文本搜索工具grep

目錄 1??核心功能?? ??2??基本語法?? 3????常用選項 & 功能詳解?? ??4??經典應用場景 & 示例?? 5????重要的提示 & 技巧?? ??6??總結?? grep 是 Linux/Unix 系統中功能強大的??文本搜索工具??,其名稱源自 …

Java面試題及詳細答案120道之(041-060)

《前后端面試題》專欄集合了前后端各個知識模塊的面試題,包括html,javascript,css,vue,react,java,Openlayers,leaflet,cesium,mapboxGL,threejs&…

【嘗試】本地部署openai-whisper,通過 http請求識別

安裝whisper的教程,已在 https://blog.csdn.net/qq_23938507/article/details/149394418 和 https://blog.csdn.net/qq_23938507/article/details/149326290 中說明。 1、創建whisperDemo1.py from fastapi import FastAPI, UploadFile, File import whisper i…