中間件筆記

一、數(shù)據(jù)庫(kù)基礎(chǔ)知識(shí)

1、請(qǐng)你說(shuō)一說(shuō)數(shù)據(jù)庫(kù)的三大范式:

數(shù)據(jù)庫(kù)的三大范式_ - visual selection.png

2、數(shù)據(jù)庫(kù)事務(wù)以及四個(gè)特性ACID、事務(wù)隔離級(jí)別、臟讀、不可重復(fù)讀和幻讀

a、事務(wù)的四大基本特性ACID(即原子性、一致性、隔離性、持久性)。

_- visual selection.png
  • 1、A (Atomicity) 原子性:所有操作要么全部成功,要么全部失敗回滾。只要有一個(gè)操作失敗,整個(gè)事務(wù)就失敗,需要回滾。
  • 2、C (Consistency) 一致性:事務(wù)開(kāi)始前和結(jié)束后,數(shù)據(jù)庫(kù)的完整性約束沒(méi)有被破壞。
    Eg:如A向B轉(zhuǎn)賬,不可能A扣了錢(qián),B卻沒(méi)收到。
  • 3、I (Isolation) 獨(dú)立性:又叫隔離性,當(dāng)多個(gè)用戶并發(fā)訪問(wèn)數(shù)據(jù)庫(kù)時(shí),比如操作同一張表時(shí),數(shù)據(jù)庫(kù)為每一個(gè)用戶開(kāi)啟的事務(wù),不能被其他事務(wù)的操作所干擾,多個(gè)并發(fā)事務(wù)之間要相互隔離。
    比如現(xiàn)在有個(gè)交易是從A賬戶轉(zhuǎn)100元至B賬戶,在這個(gè)交易還未完成的情況下,
    如果此時(shí)B查詢(xún)自己的賬戶,是看不到新增加的100元的。
  • 4、D (Durability) 持久性:持久性是指一旦事務(wù)提交后,它所做的修改將會(huì)永久的保存在數(shù)據(jù)庫(kù)上,即使出現(xiàn)宕機(jī)也不會(huì)丟失。

b、事務(wù)的隔離級(jí)別

從理論上來(lái)說(shuō), 事務(wù)應(yīng)該彼此完全隔離, 以避免并發(fā)事務(wù)所導(dǎo)致的問(wèn)題,然而, 那樣會(huì)對(duì)性能產(chǎn)生極大的影響, 因?yàn)槭聞?wù)必須按順序運(yùn)行, 在實(shí)際開(kāi)發(fā)中, 為了提升性能, 事務(wù)會(huì)以較低的隔離級(jí)別運(yùn)行,事務(wù)的隔離級(jí)別可以通過(guò)隔離事務(wù)屬性可分為四個(gè)級(jí)別。讀未提交(read uncommitted)、讀提交(read committed)、可重復(fù)讀(repeatable read)和串行化(serializable )
事務(wù)的隔離級(jí)別 - visual selection.png

讀未提交(read uncommitted)一個(gè)事務(wù)還沒(méi)提交時(shí),它做的變更就能被別的事務(wù)看到。
讀提交(read committed) 一個(gè)事務(wù)提交之后,它做的變更才會(huì)被其他事務(wù)看到。Oracle, SQL Server默認(rèn)隔
可重復(fù)讀(repeatable read):一個(gè)事務(wù)執(zhí)行過(guò)程中看到的數(shù)據(jù),總是跟這個(gè)事務(wù)在啟動(dòng)時(shí)看到的數(shù)據(jù)是一致的。當(dāng)然在可重復(fù)讀隔離級(jí)別下,未提交變更對(duì)其他事務(wù)也是不可見(jiàn)的(會(huì)有幻讀現(xiàn)象)。MySQL默認(rèn)的隔離級(jí)別
串行化(serializable):最高的隔離級(jí)別,在這個(gè)隔離級(jí)別下,不會(huì)產(chǎn)生任何異常。并發(fā)的事務(wù),就像事務(wù)是在一個(gè)個(gè)按照順序執(zhí)行一樣。對(duì)于同一行記錄,“寫(xiě)”會(huì)加“寫(xiě)鎖”,“讀”會(huì)加“讀鎖”。當(dāng)出現(xiàn)讀寫(xiě)鎖沖突的時(shí)候,后訪問(wèn)的事務(wù)必須等前一個(gè)事務(wù)執(zhí)行完成,才能繼續(xù)執(zhí)行。

  • (1)臟讀:事務(wù)A讀取了事務(wù)B還未提交的數(shù)據(jù)。
  • (2)不可重復(fù)讀:事務(wù) A 多次讀取同一數(shù)據(jù),事務(wù) B 在事務(wù)A多次讀取的過(guò)程中,對(duì)數(shù)據(jù)作了更新并提交,導(dǎo)致事務(wù)A多次讀取同一數(shù)據(jù)時(shí),讀到的數(shù)據(jù)是不同的。
  • (3)幻讀:幻讀解決了不重復(fù)讀,保證了同一個(gè)事務(wù)里,查詢(xún)的結(jié)果都是事務(wù)開(kāi)始時(shí)的狀態(tài)(一致性)。
    例如:事務(wù)T1對(duì)一個(gè)表中所有的行的某個(gè)數(shù)據(jù)項(xiàng)做了從“1”修改為“2”的操作 這時(shí)事務(wù)T2又對(duì)這個(gè)表中插入了一行數(shù)據(jù)項(xiàng),而這個(gè)數(shù)據(jù)項(xiàng)的數(shù)值還是為“1”并且提交給數(shù)據(jù)庫(kù)。 而操作事務(wù)T1的用戶如果再查看剛剛修改的數(shù)據(jù),會(huì)發(fā)現(xiàn)還有跟沒(méi)有修改一樣,其實(shí)這行是從事務(wù)T2中添加的,就好像產(chǎn)生幻覺(jué)一樣,這就是發(fā)生了幻讀。
    小結(jié):不可重復(fù)讀的和幻讀很容易混淆,不可重復(fù)讀側(cè)重于修改,幻讀側(cè)重于新增或刪除。解決不可重復(fù)讀的問(wèn)題只需鎖住滿足條件的行,解決幻讀需要鎖表。

3、數(shù)據(jù)庫(kù)索引,索引的底層使用的是什么數(shù)據(jù)結(jié)構(gòu)(B+樹(shù)),多加索引一定會(huì)好嗎?最左前綴原則。 索引的分類(lèi):聚簇索引、哈希索引、覆蓋索引

? 索引是一種幫助MySQL高效獲取數(shù)據(jù)的排好序的數(shù)據(jù)結(jié)構(gòu),解決查詢(xún)語(yǔ)句中where和order by部分的性能。
? 索引也是一張表,大大提高了查詢(xún)速度的同時(shí)降低了更新表的速度,如對(duì)表進(jìn)行INSERT、UPDATE、DELETE。

4、主從同步的原理:

  • mysql主從同步(實(shí)際場(chǎng)景:雙主方案、一主多從方案)
  1. master(主庫(kù))在每次準(zhǔn)備提交事務(wù)完成數(shù)據(jù)更新前,將改變記錄到二進(jìn)制日志(binlog)中
  2. slave(從庫(kù))發(fā)起連接,連接到master,請(qǐng)求獲取指定位置的binlog文件
  3. master創(chuàng)建【dump thread】,推送binlog的slave
  4. slave啟動(dòng)一個(gè)【I/O thread】來(lái)讀取主庫(kù)上binlog中的事件,并記錄到slave自己的中繼日志(relay log)中
  5. slave還會(huì)起動(dòng)一個(gè)【SQL thread】,該線程從relay log中讀取事件并在備庫(kù)執(zhí)行,完成數(shù)據(jù)同步
  6. slave記錄自己的binlog
  • redis主從同步的原理:
sequenceDiagram
    participant Master as 主庫(kù)(Master)
    participant Slave as 從庫(kù)(Slave)
    
    Note over Slave: 1. 建立連接
    Slave->>Master: SLAVEOF <master_ip> <port>
    
    Note over Master: 2. 全量同步(RDB)
    Master->>Master: 執(zhí)行BGSAVE生成RDB快照
    Master->>Slave: 發(fā)送RDB文件
    Slave->>Slave: 清空舊數(shù)據(jù),加載RDB
    
    Note over Master: 3. 增量同步(命令傳播)
    loop 持續(xù)同步
        Master->>Master: 接收寫(xiě)命令
        Master->>Master: 存入復(fù)制積壓緩沖區(qū)(repl_backlog)
        Master->>Slave: 異步發(fā)送寫(xiě)命令
        Slave->>Slave: 執(zhí)行接收到的命令
    end
    
    Note over Slave: 4. 斷線重連
    alt 偏移量在backlog內(nèi)
        Slave->>Master: PSYNC <runid> <offset>
        Master-->>Slave: +CONTINUE (增量同步)
    else 偏移量不在backlog內(nèi)
        Slave->>Master: PSYNC <runid> <offset>
        Master-->>Slave: +FULLRESYNC (觸發(fā)全量同步)
    end

5、數(shù)據(jù)庫(kù)中的WAL技術(shù)

WAL(Write-Ahead Logging,預(yù)寫(xiě)式日志)是現(xiàn)代數(shù)據(jù)庫(kù)系統(tǒng)中確保數(shù)據(jù)一致性和持久性的核心技術(shù)
基本原則:

  • 數(shù)據(jù)寫(xiě)入前必須先記錄日志, 只有日志寫(xiě)入成功后,修改才能應(yīng)用到實(shí)現(xiàn)數(shù)據(jù)文件。
graph LR
A[事務(wù)開(kāi)始] --> B[生成日志記錄](méi)
B --> C[日志寫(xiě)入磁盤(pán)]
C --> D[修改內(nèi)存數(shù)據(jù)]
D --> E[事務(wù)提交]

WAL技術(shù)通過(guò)精巧的日志機(jī)制,在性能與可靠性之間取得平衡,是數(shù)據(jù)庫(kù)系統(tǒng)的基石技術(shù)之一。不同數(shù)據(jù)庫(kù)的實(shí)現(xiàn)各有特點(diǎn),但核心思想高度一致。

6、MVCC機(jī)制

MVCC(Multi-Version Concurrency Control)是現(xiàn)代數(shù)據(jù)庫(kù)系統(tǒng)實(shí)現(xiàn)高并發(fā)訪問(wèn)的核心技術(shù).
通過(guò)數(shù)據(jù)多版本化解決讀寫(xiě)沖突,顯著提升系統(tǒng)并發(fā)性能。
特點(diǎn):

  • 高并發(fā): 讀寫(xiě)都通過(guò)版本號(hào)控制,事務(wù)處理時(shí)不會(huì)出現(xiàn)沖突。
  • 避免鎖競(jìng)爭(zhēng): 多版本號(hào)可以避免鎖競(jìng)爭(zhēng)。減少死鎖概率。
  • 原則:"讀不阻塞寫(xiě),寫(xiě)不阻塞讀"

mysql

1、常用操作

mysql -u<username> -p<passward> # 登陸
show databases;  # 查看數(shù)據(jù)庫(kù)
use dbName;      # 切換數(shù)據(jù)庫(kù)
show tables;     # 查看表
select * from dbName.user;  # 查看表的數(shù)據(jù)
insert into dbName.user values(1,'張三',18);  # 插入數(shù)據(jù)
update dbName.user set name='李四' where id=1;  # 更新數(shù)據(jù)
delete from dbName.user where id=1;  # 刪除數(shù)據(jù)
drop table dbName.user;  # 刪除表

create table user (
   id int not null auto_increment primary key,
   name varchar(16),
   age int default 19
)engine=innodb default charset=utf8;      # 創(chuàng)建數(shù)據(jù)庫(kù)表

select val1,val2 from dbName.tableName where [條件];  # 查詢(xún)數(shù)據(jù)
# 關(guān)于條件:1. 支持比較運(yùn)算符:=、<>、>、<、>=、<=、in、between。
#         2. 模糊查詢(xún) like, eg: like '%張%' %表示任意多個(gè)任意字符,_表示一個(gè)任意字符
#         3. 判空:is null、is not null

# 聚合查詢(xún)函數(shù): count(*)、max(id)、sum(id)、min(id)、avg(id)
# 按某個(gè)字段排序:order by id asc/desc (升序/降序)
# 按某個(gè)字段分組:group by id
# 按某個(gè)字段分頁(yè):limit start,count 開(kāi)始位置 條數(shù)

2、sql查詢(xún)句的執(zhí)行順序:

sql執(zhí)行順序 - visual selection.png

執(zhí)行順序解釋
1.from 要做數(shù)據(jù)分析,得先有個(gè)表
2.join 一個(gè)表可能還不夠,兩個(gè)表甚至多個(gè)表都可以,關(guān)聯(lián)條件啥也先不用,可以都來(lái)個(gè) 笛卡兒積先。
3.on 在諸多表左右連接后,設(shè)定兩個(gè)表之間的關(guān)聯(lián)鍵,把不符合條件的全部篩掉
4.where 上三步整合各表,形成一個(gè)統(tǒng)一大表;在此大表上,設(shè)置篩選條件
5.group by 把指定字段相同的行組合在一起,其余沒(méi)有加入group by的字段,可以用聚合函數(shù)如max/min等合并
6.having 在group by了之后,再度指定篩選條件;注意where和having是不同的,主要在于中間多了group by
7.select 在行層面的處理暫告一段落,在列層面再來(lái)一波
8.distinct 指定字段去重
9.order by 指定字段排序,升降序

3、MySQL的存儲(chǔ)引擎: InnoDB 存儲(chǔ)引擎(B+樹(shù)實(shí)現(xiàn))、 MyISAM

存儲(chǔ)引擎層負(fù)責(zé)數(shù)據(jù)的存儲(chǔ)和提取。
? InnoDB:支持事務(wù)處理,支持外鍵,支持崩潰修復(fù)能力和并發(fā)控制。如果對(duì)事物的完整性要求比較高(如銀行),要求實(shí)現(xiàn)并發(fā)控制(如售票),那么選擇InnoDB有很大的優(yōu)勢(shì)。如果需要頻繁更新、delete數(shù)據(jù),也可以選擇InnoDB,因?yàn)镮nnoDB支持事物的提交commit和回滾rollback.
? MyISAM:插入數(shù)據(jù)快,空間和內(nèi)存使用比較低。如果表主要用于插入新記錄和讀出記錄,那么選擇MyISAM能實(shí)現(xiàn)處理高效。如果應(yīng)用的完整性,并發(fā)性要求比較低,也可以使用。
? MEMORY:所以數(shù)據(jù)都在內(nèi)存中,數(shù)據(jù)處理速度快,但安全性差。它對(duì)表有要求,不能建立太大的表。只能應(yīng)用于小表,對(duì)速度要求高,對(duì)安全性要求很低的場(chǎng)景。

InnoDB->聚集索引:數(shù)據(jù)和B+Tree的節(jié)點(diǎn)存儲(chǔ)在一起;
底層的一張表只有2個(gè)文件存儲(chǔ)。.frm 表結(jié)構(gòu)、.ibd文件:存放數(shù)據(jù)庫(kù)表數(shù)據(jù)和索引。
MyISAM->非聚集索引:數(shù)據(jù)和B+Tree的節(jié)點(diǎn)分開(kāi)存儲(chǔ)。
底層的一張表有3個(gè)文件存儲(chǔ)。.frm 表結(jié)構(gòu)、.myd 即 my data,表數(shù)據(jù)文件、.myi 即 my index,索引文件

redis

1、Redis的key支持的數(shù)據(jù)結(jié)構(gòu)

  • string,list,set,zset,hash
  • 另外幾種數(shù)據(jù)結(jié)構(gòu) HyperLogLog、Geo、Pub/Sub。
  • 更高級(jí)的數(shù)據(jù)結(jié)構(gòu): Redis Module,像 BloomFilter,RedisSearch,Redis-ML。

2、Redis事務(wù)

Redis 的所有操作都是原子性的,所謂的原子性就是對(duì)數(shù)據(jù)的更改要么全部執(zhí)行,要么全部不執(zhí)行。單個(gè)操作是原子性的。多個(gè)操作也支持事務(wù),即原子性,通過(guò) MULTI 和 EXEC指令包起來(lái)。MULTI、EXEC、DISCARD、WATCH。
1、Redis通過(guò)四個(gè)命令實(shí)現(xiàn)事務(wù):WATCH,MULTI,EXEC,DISCARD
2、Redis事務(wù)以MULTI命令開(kāi)始,EXEC/DISCARD命令結(jié)束。EXEC用于提交事務(wù),DISCARD用于取消事務(wù)。
3、在開(kāi)啟事務(wù)時(shí),Redis操作命令并不會(huì)立即執(zhí)行,而是會(huì)先進(jìn)入事務(wù)隊(duì)列。Redis事務(wù)隊(duì)列是一個(gè)FIFO隊(duì)列
4、當(dāng)執(zhí)行EXEC命令時(shí),會(huì)把事務(wù)隊(duì)列中的命令逐個(gè)執(zhí)行,不會(huì)被任何命令中斷。
5、Redis中的Watch機(jī)制,在開(kāi)啟事務(wù)前,使用WATCH命令監(jiān)視指定的key,形成樂(lè)觀鎖。事務(wù)執(zhí)行時(shí),如果被WATCH的key發(fā)生了變化,則事務(wù)失效,不能執(zhí)行。
Redis事務(wù)時(shí)不支持回滾的。也就是說(shuō),如果事務(wù)中的命令執(zhí)行出錯(cuò),已經(jīng)執(zhí)行的命令不會(huì)撤回,后續(xù)的命令也會(huì)繼續(xù)執(zhí)行。Redis事務(wù)的命令分為入隊(duì)和執(zhí)行兩個(gè)階段。在入隊(duì)(進(jìn)入事務(wù)隊(duì)列)時(shí)出錯(cuò),Redis會(huì)忽略入隊(duì)出錯(cuò)的命令,不會(huì)影響后續(xù)命令入隊(duì)。執(zhí)行時(shí)出錯(cuò),出錯(cuò)命令會(huì)被Redis忽略,其他沒(méi)有出錯(cuò)的命令均會(huì)執(zhí)行。
6、Redis事務(wù)不能嵌套。如果再收到MULTI命令開(kāi)啟事務(wù),直接返回錯(cuò)誤。遇到嵌套事務(wù)返回錯(cuò)誤后,并不會(huì)影響事務(wù)隊(duì)列繼續(xù)接收命令,也不會(huì)修改事務(wù)隊(duì)列中的任何數(shù)據(jù)。
多個(gè)客戶端同時(shí)開(kāi)啟事務(wù)會(huì)怎樣?
在并發(fā)情況,很容易出現(xiàn)多個(gè)客戶端同時(shí)開(kāi)啟事務(wù)的情況。這時(shí)Redis會(huì)區(qū)分客戶端維護(hù)事務(wù)隊(duì)列嗎?另外,實(shí)際工程中為了提升性能,通常會(huì)用Redis連接池復(fù)用連接,這種情況下,會(huì)出現(xiàn)連接復(fù)用導(dǎo)致事務(wù)嵌套嗎?
Redis事務(wù)隊(duì)列是與連接綁定的,不同的連接中允許同時(shí)開(kāi)啟事務(wù),不會(huì)相互影響。
合理的事務(wù)管理器中,會(huì)在開(kāi)啟事務(wù)時(shí)綁定連接,防止連接被其他請(qǐng)求復(fù)用。不過(guò)應(yīng)用不當(dāng),會(huì)出現(xiàn)連接不能被歸還的問(wèn)題。(由此可見(jiàn),一個(gè)優(yōu)秀的事務(wù)管理器是多么重要)

Redis中的事務(wù)

  • 開(kāi)啟事務(wù)
    MULTI:開(kāi)啟事務(wù),事務(wù)塊中多條語(yǔ)句會(huì)按照順序放入隊(duì)列當(dāng)中,最后由EXEC來(lái)執(zhí)行
MULTI  
INCT key
INCR key
INCR key 
PING
GET key
  • 執(zhí)行事務(wù)
    EXEC: 執(zhí)行事務(wù)塊中的命令

  • 監(jiān)視一個(gè)或者多個(gè)key
    WATCH: 監(jiān)視一個(gè)或者多個(gè)key,如果事務(wù)在執(zhí)行之前這個(gè)key被其他命令改動(dòng),事務(wù)就會(huì)被打斷
    UNWATCH: 取消WATCH對(duì)所有的key的監(jiān)視

  • 取消事務(wù)
    DISCARD: 取消事務(wù)

MULTI
SET name hello
INCR counter4
INCR COUNTER5 
DISCARD
  • 事務(wù)中的錯(cuò)誤處理
    語(yǔ)法錯(cuò)誤: 命令不存在,參數(shù)錯(cuò)誤
    如果有語(yǔ)法錯(cuò)誤,Redis在EXEC后直接返回錯(cuò)誤,正確的命令也不會(huì)被執(zhí)行
    運(yùn)行錯(cuò)誤:指在運(yùn)行命令的時(shí)候出現(xiàn)的問(wèn)題,錯(cuò)誤的不會(huì)被執(zhí)行,正確的會(huì)被執(zhí)行
MULTI 
SET 1test2 1
SADD test2 2  # 集合操作字符串
SET test2 3
EXEC

3、redis streams 消息緩存

支持 publish/subscribe
按 key 設(shè)置過(guò)期時(shí)間,過(guò)期后將會(huì)自動(dòng)刪除。

4、持久化機(jī)制:RDB/AOF

1、RDB:是指用數(shù)據(jù)集以快照的方式將數(shù)據(jù)寫(xiě)入一個(gè)臨時(shí)文件,待系統(tǒng)恢復(fù)正常的時(shí)候,用這個(gè)臨時(shí)文件替換上次持久化的文件,達(dá)到數(shù)據(jù)恢復(fù)。
優(yōu)點(diǎn):
(1)只有一個(gè)文件 dump.rdb,方便持久化。
(2)容災(zāi)性好,一個(gè)文件可以保存到安全的磁盤(pán)。
(3)性能最大化,fork 子進(jìn)程來(lái)完成寫(xiě)操作,讓主進(jìn)程繼續(xù)處理命令,所以是 IO最大化。使用單獨(dú)子進(jìn)程來(lái)進(jìn)行持久化,主進(jìn)程不會(huì)進(jìn)行任何 IO 操作,保證了 redis的高性能)
(4)相對(duì)于數(shù)據(jù)集大時(shí),比 AOF 的啟動(dòng)效率更高。
缺點(diǎn):
數(shù)據(jù)安全性低。RDB 是間隔一段時(shí)間進(jìn)行持久化,如果持久化之間 redis 發(fā)生故障,會(huì)發(fā)生數(shù)據(jù)丟失。所以這種方式更適合數(shù)據(jù)要求不嚴(yán)謹(jǐn)?shù)臅r(shí)候。
2、AOF(Append-only file):記錄命令行操作,將其保存為 aof 文件。
優(yōu)點(diǎn):
(1)數(shù)據(jù)安全,aof 持久化可以配置 appendfsync 屬性,有 always,每進(jìn)行一次命令操作就記錄到 aof 文件中一次。
(2)通過(guò) append 模式寫(xiě)文件,即使中途服務(wù)器宕機(jī),可以通過(guò) redis-check-aof工具解決數(shù)據(jù)一致性問(wèn)題。
(3)AOF 機(jī)制的 rewrite 模式。AOF 文件沒(méi)被 rewrite 之前(文件過(guò)大時(shí)會(huì)對(duì)命令進(jìn)行合并重寫(xiě)),可以刪除其中的某些命令(比如誤操作的 flushall))
缺點(diǎn):
(1)AOF 文件比 RDB 文件大,且恢復(fù)速度慢。
(2)數(shù)據(jù)集大的時(shí)候,比 rdb 啟動(dòng)效率低。

5、redis 過(guò)期鍵的刪除策略?

redis 過(guò)期鍵的刪除策略? - visual selection.png

(1)定時(shí)刪除:在設(shè)置鍵的過(guò)期時(shí)間的同時(shí),創(chuàng)建一個(gè)定時(shí)器 timer). 讓定時(shí)器在鍵的過(guò)期時(shí)間來(lái)臨時(shí),立即執(zhí)行對(duì)鍵的刪除操作。
(2)惰性刪除:放任鍵過(guò)期不管,但是每次從鍵空間中獲取鍵時(shí),都檢查取得的鍵是否過(guò)期,如果過(guò)期的話,就刪除該鍵;如果沒(méi)有過(guò)期,就返回該鍵。
(3)定期刪除:每隔一段時(shí)間程序就對(duì)數(shù)據(jù)庫(kù)進(jìn)行一次檢查,刪除里面的過(guò)期鍵。至于要?jiǎng)h除多少過(guò)期鍵,以及要檢查多少個(gè)數(shù)據(jù)庫(kù),則由算法決定。

6、Redis 的回收策略(淘汰策略)?

volatile-lru:從已設(shè)置過(guò)期時(shí)間的數(shù)據(jù)集(server.db[i].expires)中挑選最近最少使用的數(shù)據(jù)淘汰
volatile-ttl:從已設(shè)置過(guò)期時(shí)間的數(shù)據(jù)集(server.db[i].expires)中挑選將要過(guò)期的數(shù)據(jù)淘汰
volatile-random:從已設(shè)置過(guò)期時(shí)間的數(shù)據(jù)集(server.db[i].expires)中任意選擇數(shù)據(jù)淘汰
allkeys-lru:從數(shù)據(jù)集(server.db[i].dict)中挑選最近最少使用的數(shù)據(jù)淘汰
allkeys-random:從數(shù)據(jù)集(server.db[i].dict)中任意選擇數(shù)據(jù)淘汰
no-enviction(驅(qū)逐):禁止驅(qū)逐數(shù)據(jù)
注意這里的 6 種機(jī)制,volatile 和 allkeys 規(guī)定了是對(duì)已設(shè)置過(guò)期時(shí)間的數(shù)據(jù)集淘汰數(shù)據(jù)還是從全部數(shù)據(jù)集淘汰數(shù)據(jù),后面的 lru、ttl 以及 random 是三種不同的淘汰策略,再加上一種 no-enviction 永不回收的策略。
使用策略規(guī)則:
(1)如果數(shù)據(jù)呈現(xiàn)冪律分布,也就是一部分?jǐn)?shù)據(jù)訪問(wèn)頻率高,一部分?jǐn)?shù)據(jù)訪問(wèn)頻率低,則使用 allkeys-lru
(2)如果數(shù)據(jù)呈現(xiàn)平等分布,也就是所有的數(shù)據(jù)訪問(wèn)頻率都相同,則使用allkeys-random

mongodb

文檔數(shù)據(jù)庫(kù),用C++語(yǔ)言編寫(xiě)的非關(guān)系型數(shù)據(jù)庫(kù)。文件存儲(chǔ)格式為BSON(二進(jìn)制數(shù)據(jù)流)。

1、常用操作

mongod --help           # 查看幫助信息
show dbs
use <db_name>
show collections

db.getCollectionNames().length
db.<collection_name>.find({"key" : "value"}).pretty()
db.<collection_name>.deleteMany({"key" : "value"})   # {}為空時(shí),刪除所有數(shù)據(jù)。{"kye":"value"}刪除特定數(shù)據(jù)
db.<collection_name>.drop()    # 刪除整個(gè)集合包括所有數(shù)據(jù)和索引

db.collection.insertOne() #單個(gè)文檔插入到集合中
db.collection.insertMany()# 多個(gè)文檔插入到集合中
db.collection.insert() # 單個(gè)或者多個(gè)文件插入到集合中
db.collection.updateOne()  # 更新單條
db.collection.updateMany()  # 更新多條
db.collection.deleteOne()  # 刪除單條文檔
db.collection.deleteMany()  # 刪除多條文檔

2、聚合查詢(xún)

Aggregation類(lèi)似MySQL中的count、sum、group by。聚合內(nèi)置了很多函數(shù),使用好了這些函數(shù)我們就可以統(tǒng)計(jì)出我們想要的數(shù)據(jù)

  • $project:修改輸入文檔的結(jié)構(gòu)??梢杂脕?lái)重命名、增加或刪除域,也可以用于創(chuàng)建計(jì)算結(jié)果以及嵌套文檔。
  • match**:用于過(guò)濾數(shù)據(jù),只輸出符合條件的文檔。**match:{json}使用MongoDB的標(biāo)準(zhǔn)查詢(xún)操作。
  • $limit:用來(lái)限制MongoDB聚合管道返回的文檔數(shù)。
  • $skip:在聚合管道中跳過(guò)指定數(shù)量的文檔,并返回余下的文檔。
  • $group:將集合中的文檔分組,可用于統(tǒng)計(jì)結(jié)果。
  • $sort:將輸入文檔排序后輸出。
  • $geoNear:輸出接近某一地理位置的有序文檔。
  • $unwind:將文檔中的某一個(gè)數(shù)組類(lèi)型字段拆分成多條,每條包含數(shù)組中的一個(gè)值。
  • aggregation實(shí)例
# 過(guò)濾status為A, 統(tǒng)計(jì)amount字段的總和(這個(gè)總和按cost_id分組)
db.orders.aggregate([
    {$match:{status:"A"}},
    {$group:{_id:"$cost_id", total:{$sum:"$amount"}}}
])

# collection的alias字段是否存在,如果存在,就取alias,否則取host_name字段
db.getCollection('A_collection').aggregate({
    $addFields:{
      "name":{
         $cond:[{$ne:["$alias", undefined]},"$alias","$host_name"]
      }
    },
    {
      $project:{
         "name":1
      }
    } 
})
  • aggregation實(shí)例
{ "_id" : 1, "item" : "abc1", qty: 300 }
{ "_id" : 2, "item" : "abc2", qty: 200 }
{ "_id" : 3, "item" : "xyz1", qty: 250 }
# 根據(jù)qty的值來(lái)生成新的數(shù)據(jù)(值)
db.inventory.aggregate([
  {$project:
       { item: 1,
         discount: {$cond: { if: { $gte: [ "$qty", 250 ] }, then: 30, else: 20 }}
       }
  }])
#output  discount是新的鍵,它根據(jù)cond的if判斷后,分別被賦上了相應(yīng)的值
 { "_id" : 1, "item" : "abc1", "discount" : 30 }
 { "_id" : 2, "item" : "abc2", "discount" : 20 }
 { "_id" : 3, "item" : "xyz1", "discount" : 30 }

druid

Druid的核心架構(gòu)結(jié)合了數(shù)據(jù)倉(cāng)庫(kù)(data warehouses),時(shí)序數(shù)據(jù)庫(kù)(timeseries databases),log搜索系統(tǒng)(logsearch system)三種系統(tǒng)的特點(diǎn)。
特點(diǎn):1、列式存儲(chǔ)。2、可擴(kuò)展的分布式系統(tǒng)。 3、大規(guī)模并行處理。 4、實(shí)時(shí)或者批數(shù)據(jù)攝取。 5、自修復(fù)、自平衡、易于運(yùn)維。6、.云原生(Cloud-native)和容錯(cuò)設(shè)計(jì)不會(huì)導(dǎo)致任何數(shù)據(jù)丟失。7、索引可以實(shí)現(xiàn)快速過(guò)濾。8、基于時(shí)間的分片(time-based partiotioning)。9、近似算法。10、在數(shù)據(jù)攝入時(shí)自動(dòng)化合并。

基本操作

docker run --rm -i -p 8888:8888 fokkodriesprong/docker-druid   # 啟動(dòng)druid
docker exec -it <container_id> bash # 進(jìn)入容器
curl -X POST -H "Content-Type: application/json" http://localhost:8888/druid/v2/sql --data-binary '{"query":"select * from wikipedia"}' # 查詢(xún)數(shù)據(jù)
 
http://127.0.0.1:8888 # 進(jìn)入druid console

SQLite

1、常用操作

sqlite3 -version # 查看版本
sqlite3 your-database-file.db  # 打開(kāi) SQLite 數(shù)據(jù)庫(kù)文件
.tables                   # 查看數(shù)據(jù)庫(kù)表
SELECT * FROM table_name; # 查看數(shù)據(jù)庫(kù)表
.schema                   # 查看數(shù)據(jù)庫(kù)表結(jié)構(gòu)
.exit # 退出

ETCD

一個(gè)用于配置共享服務(wù)發(fā)現(xiàn)的KV存儲(chǔ)系統(tǒng)。
特點(diǎn):- 1 鍵值對(duì)存儲(chǔ) - 2 服務(wù)注冊(cè)與發(fā)現(xiàn) - 3 消息發(fā)布與訂閱 - 4 分布式通知與協(xié)調(diào) - 5 分布式鎖 - 6 集群監(jiān)控和Leader選舉

etcdctl version   # 查看版本
etcdctl --help    # 幫助信息
etcdctl put /testdir/testkey "Hello world"  # 存儲(chǔ)數(shù)據(jù)
etcdctl get /testdir/testkey    # 查看數(shù)據(jù)
etcdctl del /testdir/testkey    # 刪除數(shù)據(jù)  成功返回1 失敗返回0
etcdctl watch /testdir/testkey --rev=1 # 監(jiān)控?cái)?shù)據(jù)變化,從修訂版本號(hào) 1 開(kāi)始監(jiān)控事件(創(chuàng)建、更新、刪除) 
etcdctl update /testdir/testkey "Hello world" --prev-value "你好"  # 更新數(shù)據(jù):只有當(dāng)鍵 /testdir/testkey 的當(dāng)前值為 "Hello world" 時(shí)。--prev-value:指定鍵的當(dāng)前預(yù)期值(類(lèi)似樂(lè)觀鎖機(jī)制)

etcdctl member list      # 查詢(xún)etcd集群實(shí)例
etcdctl member remove    # 刪除 etcd 實(shí)例到 etcd 集群中。
etcdctl member add       # 添加etcd 實(shí)例到 etcd 集群中。

InfluxDB

1、常用操作

安裝: rpm -ivh xxx.rpm
server啟動(dòng): /usr/bin/influxd
配置文件的路徑: /etc/influxdb/influxdb.conf
注意:增加數(shù)據(jù)采用insert的方式,要注意的是 InfluxDB的insert中,表名與數(shù)據(jù)之間用逗號(hào)(,)分隔,tag和field之間用 空格分隔,多個(gè)tag或者多個(gè)field之間用逗號(hào)(,)分隔。

  • 基本sql語(yǔ)法:
create databases <db_name>;
show databases;
use <db_name>;
show measurements;
insert <measurement_name>,host=127.0.0.1,monitor_name=test count=1,cpu=0.1 1435362189575692182  //插入數(shù)據(jù)
         //host=127.0.0.1,monitor_name=test --> tag
         //count=1,cpu=0.1   --> field                  創(chuàng)建表和增加數(shù)據(jù)是一樣的
         //1435362189575692182   --> timestamp
precision rfc3339   -- 之后再查詢(xún),時(shí)間就是rfc3339標(biāo)準(zhǔn)格式【這個(gè)語(yǔ)句后面不加;】          
select * from <measurement_name> order by time desc limit 10;  //查詢(xún)升序的10條數(shù)據(jù)
drop measurement <measurement_name>
show tag keys;              // 查看一個(gè)measurement中所有的tag key
show field keys;            // 查看一個(gè)measurement中所有的field key
show retention policies;    // 查看一個(gè)measurement中所有的保存策略(可以有多個(gè),一個(gè)標(biāo)識(shí)為default)

# 支持豐富的聚合函數(shù)

2、保存策略與連續(xù)查詢(xún)

數(shù)據(jù)庫(kù)保存策略的CURD:提供數(shù)據(jù)保存策略指定數(shù)據(jù)保留時(shí)間,超過(guò)指定時(shí)間自動(dòng)刪除.

show retention policies on <db_name>  //查看當(dāng)前數(shù)據(jù)庫(kù)Retention Policies
create retention policy <rp_name> on <db_name> duration 3w replication 1 default
         //rp_name:策略名;
         //3w:保存3周,3周之前的數(shù)據(jù)將被刪除,influxdb具有各種事件參數(shù),比如:h,d,w
         //replication 1:副本個(gè)數(shù),一般為1就可以了;
         //default:設(shè)置為默認(rèn)策略
alter retention policy <rp_name> on <db_name> duration 30d default
drop retention policy <rp_name>
//連續(xù)查詢(xún)Continuous Queries:(數(shù)據(jù)統(tǒng)計(jì)采樣)
show continuous queries;
create continuous querie <cq_name> on <db_name> begin select sum(count) into <new_ms_name> from <ms_name> group by time(30m) end
      //間隔30分鐘計(jì)算一次count的和,保存至新的ms. 其中:sum(count):計(jì)算總和,30m:時(shí)間間隔為30分鐘;  
drop cotinuous query <cq_name> on <db_name>

3、curl交互

curl -G 'http://localhost:8086/query?pretty=true' --data-urlencode "db=testDb" --data-urlencode "q=select + from test order by time desc"
curl -i -XPOST 'http://localhost:8086/write?db=testDb' --data-binary 'test,host=127.0.0.1,monitor_name=test count=1'
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容