1. 程式人生 > >Redis自學筆記:3.3入門-散列類型

Redis自學筆記:3.3入門-散列類型

偽代碼 header cond 代碼 time 日誌 不執行 散列類型 keys

3.3散列類型

3.3.1介紹

  • 散列類型不能嵌套其他數據類型,一個散列類型可以包含至多232-1個字段
    散列類型適合存儲對象:使用對象類別和ID構成鍵名,使用字段表示對象的數據,
    而字段值則存儲屬性值.

圖3-5使用散列類型存儲汽車對象結構圖

字段 字段值
car:2 color 白色
car:2 name 奧迪
car:2 price 90萬

3.3.2命令

  1. 賦值與取值

    hset key field value
    單個字段賦值
    hget key field
    單個字段取值
    hmset key field value [field value ...]
    多個字段賦值
    hmget key field [field ...]


    多個字段取值
    hgetall key
    獲取所有字段和字段值

        127.0.0.1:6379> hset car price 500
        1
        127.0.0.1:6379> hset car name BMW
        1
        127.0.0.1:6379> hget car name
        BMW
        127.0.0.1:6379> hget car price
        500
    • hset不區分插入和更新操作(修改數據時不用判斷字段是插入還是更新)
      當執行的是插入操作,hset命令返回1.當執行的更新操作是,hset命令返回0.
    • 在redis中,每個鍵都屬於一個明確的數據類型.當需要同時設置多個字段的
      值時,可以使用hmset.
        127.0.0.1:6379> hmset car name BMW price 500
        OK
        127.0.0.1:6379> hmget car name price
        BMW
        500
        127.0.0.1:6379> hgetall car
        name
        BMW
        price
        500
  2. 判斷字段是否存在
    hexists key field

        127.0.0.1:6379> hexists car name
        1
  3. 當字段不存在時賦值
    hsetnx key field value

  • 如果字段已經存在,hsetnx命令將不執行任何操作
    127.0.0.1:6379> hsetnx car color red 1 127.0.0.1:6379> hget car color red 127.0.0.1:6379> hsetnx car color white 0 127.0.0.1:6379> hget car color red
  1. 增加數字
    hincrby key field increment

        127.0.0.1:6379> hget person score
        60
  2. 刪除字段
    hdel key field [field...]

        127.0.0.1:6379> hmset car name BWM color red
        OK
        127.0.0.1:6379> hgetall car
        name
        BWM
        color
        red
        127.0.0.1:6379> hdel car color
        1
        127.0.0.1:6379> hgetall car
        name
        BWM

3.3.3實踐

  1. 存儲文章數據
    3.2.3節介紹了將文章對象序列化後使用一個字符串類型鍵儲存,可是這種方法
    無法提供對單個字段的原子讀寫操作,從而產生競態條件,如兩個客戶端同時獲
    得並反序列化某個文章的數據,然後分別修改不同的屬性後存入,顯然後存入的
    數據會覆蓋之前的數據,最後只會有一個屬性被修改.並且即使只需要修改文章
    標題,程序也不得不將文章內容在內所有文章數據取出並反序列化,比較消耗資源

    • 競態條件(race condition),從多進程間通信的角度來講,是指兩個或多個
      進程對共享的數據進行讀或寫的操作時,最終的結果取決於這些進程的執行順序。

    使用多個字符串類型來存儲一篇文章數據:
    圖3-6使用多個字符串類型存儲一個對象

    鍵值
    post:42:title 第一篇日誌
    post:42:author 小白
    post:42:time 2012年9月21日
    post:42:content 今天是星期五...
    • 優點:無論獲取還是修改文章數據,都可以只對某一屬性進行操作,十分方便

    使用一個散列類型鍵存儲一個對象:
    圖3-7使用散列類型鍵存儲一個對象

    字段 字段值
    post:42 --> title --> 第一篇日誌
    post:42 --> author --> 小白
    post:42 --> time --> 2012年9月21日
    post:42 --> content --> 今天是星期五...
    • 優點:比上圖方法看起來更加直觀,也容易維護,而且同樣的數據散列類型往往比字符串類型更加節約空間
  2. 存儲文章縮寫名
    我們可以使用一個散列類型的鍵slug.to.id來存儲文章縮寫名和ID之間的映射關系
    這樣我們就可以使用hexists來判斷縮寫名是否存在,使用hget命令來獲取縮寫名對應的文章的ID.
    現在發布文章可以修改成如下偽代碼:

    $postID = incr posts:count
    判斷用戶輸入的slug(文章縮寫名)是否可用,如果可用則記錄
    $isSlugAvailable = hsetnx slug.to.id,$slug,$postID
    if $isSlugAvailable is 0
    # slug已經用過了,需要提示用戶更換slug
    # 這裏為了演示方便直接退出
        exit
    hmset post:$postID,title,$title,content,$content,slug,$lug,...

用戶訪問時獲取文章ID偽代碼:

    $postID = hget slug.to.id,$slug
    if not $postID
        print 文章不存在
        exit
    $post = hgetall post:$postID
    print 文章標題:$post.title

如果修改文章的縮略名一定要修改slug.to.id鍵對應的字段,偽代碼:

    # 判斷新的slug是否可用
    $isSlugAvailable = hsetnx slug.同.id,$newSlug,42
    if $isSlugAvailable is 0
        exit
    # 獲得舊的縮略名
    $oldSlug = hget post:42,slug
    # 設置新的縮略名
    hset post: 42 ,slug,$newSlug
    # 刪除舊的縮略名
    hdel slug.to.id,$oldSlug

3.3.4命令拾遺

  1. 只獲取字段名或字段值
    hkeys key : 獲取鍵中所有字段
    hvals key : 獲取鍵中所有字段值

     127.0.0.1:6379> hmset car color red name BWM
     OK
     127.0.0.1:6379> hkeys car
     color
     name
     127.0.0.1:6379> hvals car
     red
     BWM
  2. 獲取字段數量 : hlen key

     127.0.0.1:6379> hlen car
     2

Redis自學筆記:3.3入門-散列類型