Redis入門篇-五種基本數(shù)據(jù)類型及使用場(chǎng)景

前期準(zhǔn)備工作(如無需要可直接跳過)

redis安裝

具體的安裝教程可參考之前的章節(jié)(http://www.reibang.com/p/91f90adb782f

啟動(dòng)redis server(如果沒有redis install角雷,可在src目錄下找到啟動(dòng)命令)

執(zhí)行bin/redis-server命令矢沿,出現(xiàn)如下圖就說明啟動(dòng)成功

redis server啟動(dòng)

bin/redis-server命令后面可以指定redis的配置文件(配置文件中配置了一些參數(shù))坞淮,具體的配置文件可關(guān)注博主菱蔬,后期會(huì)不斷更新麦牺,共同進(jìn)步寒亥;

啟動(dòng)redis client(如果沒有redis install洒忧,可在src目錄下找到啟動(dòng)命令)

執(zhí)行bin/redis-cli [-h ip] [-p port]运授,出現(xiàn)如下圖所示說明客戶端啟動(dòng)并連接成功

redis client啟動(dòng)

執(zhí)行ping命令烤惊,測(cè)試是否連接成功,出現(xiàn)如下圖所示表示連接成功
ping測(cè)試連接

redis的五種類型

  • string:字符串類型
  • list:列表
  • hash:hash吁朦,類似于Java中的hashMap數(shù)據(jù)結(jié)構(gòu)
    • 有序柒室,順序?yàn)椴迦氲捻樞?/li>
    • 允許重復(fù)值
  • set:無序去重列表,與Java中的set類似
    • 無序
    • 對(duì)值進(jìn)行去重
  • zset(sorted set):有序去重列表
    • 結(jié)構(gòu)體中有score的值逗宜,會(huì)根據(jù)這個(gè)score的值進(jìn)行排序
    • 對(duì)值進(jìn)行去重

string

部分基本命令
命令 解釋說明 語法 實(shí)例
set 給一個(gè)key設(shè)置string的值 set key value set k1 v1
mset set的批量操作 mset key value [key value ...] mset k1 v1 k2 v2
setex set增強(qiáng)雄右,添加過期時(shí)間 setex key seconds value setex k1 10 v1
setnx 只有當(dāng)key不存在的時(shí)候才會(huì)設(shè)置值 setnx key value setnx k1 v1
setrange 重置指定位置的字符 setrange key offset value setrange k1 1 v2
get 獲取指定key的string值 get key get k1
append 追加string值到一個(gè)key的末尾 append key value append k1 v2
mget get的批量操作 mget key [key ...] mget k1 k2 k3
incr 對(duì)int類型的值+1操作 incr key incr k1
incrby 對(duì)int類型的值+整數(shù)操作 incrbykey increment incrby k1 10
incrbyfloat 對(duì)int類型的值+浮點(diǎn)數(shù)操作 incrbyfloat key increment incrbyfloat k1 0.5
decr 對(duì)int類型的值-1操作 decr key decr k1
decrby 對(duì)int類型的值-整數(shù)操作 decrby key decrement decrby k1 10
decrbyfloat 對(duì)int類型的值-浮點(diǎn)數(shù)操作 decrbyfloat key decrement decrbyfloat k1 0.5

提示:可使用help @string查看所有string的相關(guān)命令以使用語法與含義空骚;

應(yīng)用場(chǎng)景
  • 分布式鎖的實(shí)現(xiàn)(簡(jiǎn)易版jedis)
public class SimpleDistributedLock {
    // treadcount
    private static final int threadCount = 100;
    private static CountDownLatch countDownLatch = new CountDownLatch(threadCount);
    // 1000個(gè)庫存
    private static int inv = 1;
    // 鎖的key
    private static final String lockKey = "distributedLock:simple";
    // 鎖超時(shí)時(shí)間
    private static final long expireSeconds = 10;
    // redisson
    private static RedissonClient redissonClient;
    // redis host
    private static final String redisHost = "127.0.0.1";
    // redis port
    private static final int redisPort = 6379;
    // 初始化連接redis
    static {
        Config config = new Config();
        config.useSingleServer().setAddress(redisHost + ":" + redisPort);
        redissonClient = Redisson.create(config);
    }
    public static void main(String[] args) throws InterruptedException {
        // 模擬并發(fā) 扣減庫存
        for (int i = 0; i < threadCount; i++) {
            new Thread(() -> {
                RLock lock = redissonClient.getLock(lockKey);
                try {
                    // 設(shè)置過期時(shí)間 并 加鎖(獲取鎖)
                    lock.lock(expireSeconds, TimeUnit.SECONDS);
                    // 業(yè)務(wù) 扣減庫存
                    if (inv > 0) {
                        inv--;
                    }

                } catch (Exception e) {
                    // 回滾業(yè)務(wù)操作
                } finally {
                    lock.unlock();
                    countDownLatch.countDown();
                }
            }).start();
        }
        countDownLatch.await();
        System.out.println(inv);
        redissonClient.shutdown();
    }
}
  • 分布式計(jì)數(shù)器
public class Counter {
    private static int count = 0;
    // treadcount
    private static final int threadCount = 100;
    private static CountDownLatch countDownLatch = new CountDownLatch(threadCount);
    // 鎖的key
    private static final String lockKey = "distributedLock:simple";
    // 鎖超時(shí)時(shí)間
    private static final long expireSeconds = 10;
    // redisson
    private static RedissonClient redissonClient;
    // redis host
    private static final String redisHost = "127.0.0.1";
    // redis port
    private static final int redisPort = 6379;
    // 初始化連接redis
    static {
        Config config = new Config();
        config.useSingleServer().setAddress(redisHost + ":" + redisPort);
        redissonClient = Redisson.create(config);
    }
    public static void main(String[] args) throws InterruptedException {
        for (int i = 0; i < threadCount; i++) {
            new Thread(() -> {
                RLock lock = redissonClient.getLock(lockKey);
                try {
                    lock.lock(expireSeconds, TimeUnit.SECONDS);
                    // 業(yè)務(wù)操作
                    count++;
                } finally {
                    countDownLatch.countDown();
                    lock.unlock();
                }
            }).start();
        }
        countDownLatch.await();
        System.out.println(count);
        redissonClient.shutdown();
    }
}
  • 統(tǒng)計(jì)用戶一年內(nèi)的登錄情況
# uid為key,每一位代表著一年中的一天
# 2016123240用戶在第一天登錄過
127.0.0.1:6379> SETBIT uid_2016123240 0 1
(integer) 0
# 2016123240用戶在第八天登錄過
127.0.0.1:6379> SETBIT uid_2016123240 7 1
(integer) 0
# 2016123240用戶在第二十二天登錄過
127.0.0.1:6379> SETBIT uid_2016123240 21 1
(integer) 0
# 2016123240用戶在第三十一天登錄過
127.0.0.1:6379> SETBIT uid_2016123240 30 1
(integer) 0
# 2016123240用戶在第五十六天登錄過
127.0.0.1:6379> SETBIT uid_2016123240 55 1
(integer) 0
# 2016123240用戶在第三百六十六天登錄過
127.0.0.1:6379> SETBIT uid_2016123240 365 1
(integer) 0
# 獲取2016123240用戶在這一年內(nèi)的登錄次數(shù)
127.0.0.1:6379> BITCOUNT uid_2016123240 0 -1
(integer) 6
  • 統(tǒng)計(jì)近7天登錄過的用戶數(shù)
127.0.0.1:6379> SETBIT 20210628 1 1
(integer) 0
127.0.0.1:6379> SETBIT 20210628 2 1
(integer) 0
127.0.0.1:6379> SETBIT 20210628 3 1
(integer) 0
127.0.0.1:6379> SETBIT 20210628 4 1
(integer) 0
127.0.0.1:6379> SETBIT 20210629 1 1
(integer) 0
127.0.0.1:6379> SETBIT 20210629 6 1
(integer) 0
127.0.0.1:6379> SETBIT 20210629 5 1
(integer) 0
127.0.0.1:6379> SETBIT 20210629 2 1
(integer) 0
127.0.0.1:6379> SETBIT 20210630 2 1
(integer) 0
127.0.0.1:6379> SETBIT 20210630 1 1
(integer) 0
127.0.0.1:6379> SETBIT 20210630 9 1
(integer) 0
127.0.0.1:6379> SETBIT 20210630 5 1
(integer) 0
127.0.0.1:6379> SETBIT 20210701 1 1
(integer) 0
127.0.0.1:6379> SETBIT 20210701 6 1
(integer) 0
127.0.0.1:6379> SETBIT 20210701 3 1
(integer) 0
127.0.0.1:6379> SETBIT 20210701 2 1
(integer) 0
127.0.0.1:6379> SETBIT 20210702 1 1
(integer) 0
127.0.0.1:6379> SETBIT 20210702 2 1
(integer) 0
127.0.0.1:6379> SETBIT 20210702 10 1
(integer) 0
127.0.0.1:6379> SETBIT 20210703 1 1
(integer) 0
127.0.0.1:6379> SETBIT 20210703 2 1
(integer) 0
127.0.0.1:6379> SETBIT 20210703 6 1
(integer) 0
127.0.0.1:6379> SETBIT 20210704 1 1
(integer) 0
127.0.0.1:6379> BITOP or orResult 20210628 20210629 20210630 20210701 20210702 20210703 20210704
(integer) 2
127.0.0.1:6379> BITCOUNT orResult 0 -1
(integer) 8
  • 統(tǒng)計(jì)最近7天連續(xù)登錄的用戶數(shù)
127.0.0.1:6379> SETBIT 20210628 1 1
(integer) 0
127.0.0.1:6379> SETBIT 20210628 2 1
(integer) 0
127.0.0.1:6379> SETBIT 20210628 3 1
(integer) 0
127.0.0.1:6379> SETBIT 20210628 4 1
(integer) 0
127.0.0.1:6379> SETBIT 20210629 1 1
(integer) 0
127.0.0.1:6379> SETBIT 20210629 6 1
(integer) 0
127.0.0.1:6379> SETBIT 20210629 5 1
(integer) 0
127.0.0.1:6379> SETBIT 20210629 2 1
(integer) 0
127.0.0.1:6379> SETBIT 20210630 2 1
(integer) 0
127.0.0.1:6379> SETBIT 20210630 1 1
(integer) 0
127.0.0.1:6379> SETBIT 20210630 9 1
(integer) 0
127.0.0.1:6379> SETBIT 20210630 5 1
(integer) 0
127.0.0.1:6379> SETBIT 20210701 1 1
(integer) 0
127.0.0.1:6379> SETBIT 20210701 6 1
(integer) 0
127.0.0.1:6379> SETBIT 20210701 3 1
(integer) 0
127.0.0.1:6379> SETBIT 20210701 2 1
(integer) 0
127.0.0.1:6379> SETBIT 20210702 1 1
(integer) 0
127.0.0.1:6379> SETBIT 20210702 2 1
(integer) 0
127.0.0.1:6379> SETBIT 20210702 10 1
(integer) 0
127.0.0.1:6379> SETBIT 20210703 1 1
(integer) 0
127.0.0.1:6379> SETBIT 20210703 2 1
(integer) 0
127.0.0.1:6379> SETBIT 20210703 6 1
(integer) 0
127.0.0.1:6379> SETBIT 20210704 1 1
(integer) 0
127.0.0.1:6379> BITOP and andResult 20210628 20210629 20210630 20210701 20210702 20210703 20210704
(integer) 2
127.0.0.1:6379> BITCOUNT andResult 0 -1
(integer) 1

list

部分基本命令
命令 解釋說明 語法 實(shí)例
lpush 添加一個(gè)或者多個(gè)值到list中 lpush key value [value ...] lpush k1 v1 v2
lpop 移除且獲取列表中第一個(gè)元素 lpop key lpop k1
llen 獲取列表長(zhǎng)度 llen key llen k1
lindex 獲取列表中指定index的值 lindex key index lindex k1 0
linsert 向列表中指定元素前/后插入元素 linsert key before/after pivot value linsert k1 after v1
lrange 從列表中獲取范圍的值 lrange key start stop lrange k1 0 -1
lpushx 如果list存在擂仍,則添加一個(gè)值到list中 lpushx key value lpushx k1 v1
lrem 從列表中刪除指定個(gè)數(shù)的指定元素 lrem key count value lrem k1 2 v1
lset 將列表中指定index的值設(shè)置為value lset key index value lset k1 1 v1
ltrim 將列表截取指定范圍 ltrim key start stop ltrim k1 1 2
rpush 添加一個(gè)或者多個(gè)值到list最后中 rpush key value [value ...] rpush k1 v1 v2
rpop 移除且獲取列表中最后一個(gè)元素 rpop key rpop k1
rpushx 如果list存在囤屹,則添加一個(gè)值到list最后 rpushx key value rpushx k1 v1
rpoplpush 移除一個(gè)列表中的最后一個(gè)元素,并將這個(gè)元素添加到另一個(gè)列表的第一個(gè)元素并返回 rpoplpush source destination rpoplpush k1 k2
blpop 移除且獲取第一個(gè)元素(阻塞直到元素存在) BLPOP key [key ...] timeout blpop k1 10
brpop 移除且獲取最后一個(gè)元素(阻塞直到元素存在) BRPOP key [key ...] timeout brpop k1 10
brpoplpush 移除一個(gè)列表中的最后一個(gè)元素逢渔,并將這個(gè)元素添加到另一個(gè)列表的第一個(gè)元素并返回(阻塞直到元素存在) brpoplpush source destination timeout brpoplpush k1 k2 10
應(yīng)用場(chǎng)景
  • 消息隊(duì)列:主要是通過blpush+brpop實(shí)現(xiàn)肋坚;
  • 常用數(shù)據(jù)結(jié)構(gòu)實(shí)現(xiàn)
    • lpush + rpop 實(shí)現(xiàn)隊(duì)列;
    • lpush + lpop 實(shí)現(xiàn)棧肃廓;

hash

部分基本命令
命令 解釋說明 語法 實(shí)例
hget 獲取hash的屬性的值 hget key field hget k1 name
hgetall 獲取所有的hash的屬性和值 hgetall key hgetall k1
hmget 批量獲取hash的屬性的值 hmget key field [field ...] hmget k1 name age
hset 設(shè)置hash的指定屬性的值 hset key field value hset k1 name n1
hsetnx 如果不存在智厌,則設(shè)置hash的指定屬性的值 hsetnx key field value hsetnx k1 name n1
hmset 批量設(shè)置hash的指定屬性的值 hmset key field value [field value ...] hmset k1 name n1 age 18
hdel 刪除指定key的屬性 hdel key field [field ...] hdel k1 name age
hkeys 獲取key的所有的屬性 hkeys key hkeys k1
hvals 獲取key的所有屬性的值 hvals key hvals k1
hstrlen 獲取指定key的指定屬性的值的長(zhǎng)度 hstrlen key field hstrlen k1 name
hlen 獲取指定key的屬性個(gè)數(shù) hlen key hlen k1
hincrby 指定key的指定屬性值增加整數(shù)值 hincrby key field increment hincrby k1 age 5
hincrbyfloat 指定key的指定屬性值增加浮點(diǎn)值 hincrbyfloat key field increment hincrbyfloat k1 age 5.5
hexists 判斷是否存在某一個(gè)屬性 hexists key field hexists k1 name
應(yīng)用場(chǎng)景
  • 存儲(chǔ)對(duì)象(object):set user name zhangsan age 13
  • 購(gòu)物車:
    • 添加到購(gòu)物車:hset shop_car product_1001 1
    • 增加商品個(gè)數(shù):hincrby shop_car product_1001 2
    • 刪除商品:hdel shop_car product_1001
    • 計(jì)算購(gòu)物車商品種類數(shù):hlen shop_car

set

部分基本命令
命令 解釋說明 語法 實(shí)例
sadd 添加一個(gè)或多個(gè)元素 sadd key member [member ...] sadd k1 v1 v2 v3
scard 獲取set的元素個(gè)數(shù) scard key scard k1
sdiff 差集 sdiff key [key ...] sdiff k1 k2
sdiffstore 計(jì)算差集并將結(jié)果存儲(chǔ)在另一個(gè)key sdiffstore destination key [key ...] sdiffstore result k1 k2
sinter 交集 sinter key [key ...] sinter k1 k2
sinterstore 計(jì)算交集并將結(jié)果存儲(chǔ)在另一個(gè)key sinterstore destination key [key ...] sinterstore result k1 k2
sismember 判斷是否存在值 sismember key member sismember k1 v1
smembers 獲取set的所有值 smember key smember k1
smove 移動(dòng)set的指定值到另一個(gè)set中 smove source destination member smove k1 target v1
spop 移除并返回指定個(gè)數(shù)的數(shù) spop key [count] spop k1 2
srandmember 獲取指定范圍的一個(gè)或多個(gè)值 srandmember key [count] srandmember k1 2
srem 刪除指定值 srem key member [member ...] srem k1 v1
sscan 迭代 sscan key cursor [MATCH pattern] [COUNT count] ``
sunion 并集 sunion key [key ...] sunion k1 k2
sunionstore 計(jì)算并集并將結(jié)果存儲(chǔ)到新的set中 sunionstore destination key [key ...] sunionstore result k1 k2
應(yīng)用場(chǎng)景
  • 微博關(guān)注/粉絲列表:sadd follow 1 2 3/ sadd fans 1 2 3
  • 共同關(guān)注列表:sinter follow1 follow2
  • 猜你喜歡:sdiff follow1 follow2
  • 隨機(jī)抽獎(jiǎng):spop award_pool 10

zset

部分基本命令
命令 解釋說明 語法 實(shí)例
zadd 添加一個(gè)或多個(gè)元素(帶有score) zadd key score member [score member ...] zadd k1 1 v1 2 v2
zcard 獲取set的元素個(gè)數(shù) zcard key zcard k1
zcount 計(jì)算value在min-max中的個(gè)數(shù) zcount key min max zcount k1 1 10
zincrby 指定值增加指定整數(shù)值 zincrby key increment member zincrby k1 10 v1
zinterstore 交集并將結(jié)果存儲(chǔ)到另一個(gè)zset zinterstore destination numkeys key [key ...] [WEIGHTS weight] [AGGREGATE SUM] zinterstore result k1 k2
zlexcount 計(jì)算zset中score在min-max的值得個(gè)數(shù) zlexcount key min max zlexcount k1 1 10
zpopmax 彈出并返回count個(gè)最高分的元素 zpopmax key [count] zpopmax k1 2
zpopmin 彈出并返回count個(gè)最低分的元素 zpopmin key [count] zpopmin k1 2
zrangebyscore 獲取根據(jù)分?jǐn)?shù)獲取指定范圍內(nèi)的值 zrangebyscore key min max [WITHSCORES] [LIMIT offset count] zrangebyscore k1 1 10
zrank 獲取指定元素的index zrank key member zrank k1 v1
zscan 迭代 zscan key cursor [MATCH pattern] [COUNT count] ``
zscore 獲取指定值得score zscore key member zscore k1 v1
zunionstore 計(jì)算并集并將結(jié)果存儲(chǔ)到另一個(gè)zset zunionstore destination numkeys key [key ...] [WEIGHTS weight] [AGGREGATE SUM] zset result k1 k2
zrem 刪除一個(gè)或多個(gè)元素 zrem key member [member ...] zrem k1 v1 v2 v3
應(yīng)用場(chǎng)景
  • 微博熱搜
  • 最新列表

應(yīng)用場(chǎng)景實(shí)戰(zhàn),后續(xù)待更新亿昏,如果您覺得有幫助峦剔,麻煩點(diǎn)個(gè)三連,給個(gè)關(guān)注角钩。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末吝沫,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子递礼,更是在濱河造成了極大的恐慌惨险,老刑警劉巖,帶你破解...
    沈念sama閱讀 222,590評(píng)論 6 517
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件脊髓,死亡現(xiàn)場(chǎng)離奇詭異辫愉,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)将硝,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 95,157評(píng)論 3 399
  • 文/潘曉璐 我一進(jìn)店門恭朗,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人依疼,你說我怎么就攤上這事痰腮。” “怎么了律罢?”我有些...
    開封第一講書人閱讀 169,301評(píng)論 0 362
  • 文/不壞的土叔 我叫張陵膀值,是天一觀的道長(zhǎng)。 經(jīng)常有香客問我误辑,道長(zhǎng)沧踏,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 60,078評(píng)論 1 300
  • 正文 為了忘掉前任巾钉,我火速辦了婚禮翘狱,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘砰苍。我一直安慰自己盒蟆,他們只是感情好踏烙,可當(dāng)我...
    茶點(diǎn)故事閱讀 69,082評(píng)論 6 398
  • 文/花漫 我一把揭開白布师骗。 她就那樣靜靜地躺著历等,像睡著了一般。 火紅的嫁衣襯著肌膚如雪辟癌。 梳的紋絲不亂的頭發(fā)上寒屯,一...
    開封第一講書人閱讀 52,682評(píng)論 1 312
  • 那天,我揣著相機(jī)與錄音黍少,去河邊找鬼寡夹。 笑死,一個(gè)胖子當(dāng)著我的面吹牛厂置,可吹牛的內(nèi)容都是我干的菩掏。 我是一名探鬼主播,決...
    沈念sama閱讀 41,155評(píng)論 3 422
  • 文/蒼蘭香墨 我猛地睜開眼昵济,長(zhǎng)吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼智绸!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起访忿,我...
    開封第一講書人閱讀 40,098評(píng)論 0 277
  • 序言:老撾萬榮一對(duì)情侶失蹤瞧栗,失蹤者是張志新(化名)和其女友劉穎,沒想到半個(gè)月后海铆,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體迹恐,經(jīng)...
    沈念sama閱讀 46,638評(píng)論 1 319
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 38,701評(píng)論 3 342
  • 正文 我和宋清朗相戀三年卧斟,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了殴边。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 40,852評(píng)論 1 353
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡珍语,死狀恐怖锤岸,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情廊酣,我是刑警寧澤能耻,帶...
    沈念sama閱讀 36,520評(píng)論 5 351
  • 正文 年R本政府宣布,位于F島的核電站亡驰,受9級(jí)特大地震影響晓猛,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜凡辱,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 42,181評(píng)論 3 335
  • 文/蒙蒙 一戒职、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧透乾,春花似錦洪燥、人聲如沸磕秤。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,674評(píng)論 0 25
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽市咆。三九已至,卻和暖如春再来,著一層夾襖步出監(jiān)牢的瞬間蒙兰,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,788評(píng)論 1 274
  • 我被黑心中介騙來泰國(guó)打工芒篷, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留搜变,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 49,279評(píng)論 3 379
  • 正文 我出身青樓针炉,卻偏偏與公主長(zhǎng)得像挠他,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子篡帕,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,851評(píng)論 2 361

推薦閱讀更多精彩內(nèi)容