簡體   English   中英

使用兩個索引將數據存儲在文件中

[英]Store data in the file with two indexes

我正在尋找一種在文件中存儲大量數據的方法。 附加要求是:它應該被索引,integer 字段上的兩個索引應該允許非常快速地選擇一組特定的數據。

詳細信息:數據記錄是一組固定長度的 3 個整數,如下所示:

一個(整數)| B (整數) | N(整數)

A 和 B 是可索引列,而 N 只是一個數據值。

該數據集可能包含數十億條記錄(例如 30M),並且應該有一種方法可以盡快 select 所有具有 A= 的記錄。 或者盡可能快地用 B= 記錄。

除了 MySQL 和 PHP 之外,我不能使用任何其他技術,你可以說:“哇,你可以使用 MySQL。”。 當然,我已經在使用它,但是由於 MySQL 的額外數據,我的數據庫占用的空間比它應該占用的空間多 10 倍。 加上索引數據。

所以我正在尋找基於文件的解決方案。

有沒有現成的算法來實現這個? 還是源碼解決方案?

謝謝!

更新1:

CREATE TABLE `w_vectors` (
    `wid` int(11) NOT NULL,
    `did` int(11) NOT NULL,
    `wn` int(11) NOT NULL DEFAULT '0',
    UNIQUE KEY `did_wn` (`did`,`wn`),
    KEY `wid` (`wid`),
    KEY `did` (`did`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_520_ci

更新 2:

此表的目標是存儲基於單詞的搜索應用程序的文檔與單詞向量。 該表以緊湊的形式存儲所有文檔中的所有單詞(wid 是單詞詞匯表中的單詞 ID,did 是文檔 ID,wn 是文檔中單詞的編號)。 這很好用,但是,如果你有 1000000 個文檔,每個文檔平均包含 10k 個單詞,這個表就會變得非常大,比如 100 億行。 行大小為 34 字節時,它變成了一個 340 Gb 的結構,僅用於 100 萬個文檔......,不好嗎? 正確的?

我正在尋找一種優化它的方法。

如果您必須使用 MySQL,您可以嘗試:

  • 將表轉換為 MyISAM,它比 InnoDB 占用更少的空間,並且允許每個表有多個索引。 我很少推薦 MyISAM,因為它不支持 ACID 屬性。 但是,如果您選擇使用基於文件的解決方案,那么它也不支持 ACID。

  • 使用 MySQL 中壓縮數據的各種解決方案之一。 這里有一個很好的比較: https://www.percona.com/blog/2018/11/23/compression-options-in-mysql-part-1/

你也可以改變

UNIQUE KEY `did_wn` (`did`,`wn`)

PRIMARY KEY(did, wn)

並擺脫

INDEX(did)

因為該復合索引負責對did的查詢。

有了那個PK,這些將非常有效:

... WHERE did = 123
... WHERE did = 123 AND wn = 456
... WHERE wn = 456 AND did = 123

同時,您的INDEX(wid)使任何測試單個 wid 值或一系列 wid 的WHERE子句受益。

由於我不知道您原來AB ,因此我無法根據真實的列名回答您的問題。 反正:

應該有一種方法可以盡快 select 所有帶有 A= 的記錄。 或者盡可能快地用 B= 記錄。

對於那些,你需要

INDEX(A)  -- or any index _starting with_ A
INDEX(B)  -- or any index _starting with_ B

但是,如果其中任何一個是did ,請不要添加它。 (PK 將負責使其快速。

另外,使用 InnoDB,而不是 MyISAM。 唉,在您的情況下,這會導致“空間比應有的空間多 10 倍”。 如果您選擇使用 MyISAM,我將需要重新開始索引建議。

一旦你 map A 和 B 到列名,我再給你一個提示。

更多索引討論: http://mysql.rjweb.org/doc.php/index_cookbook_mysql

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM