工作中數(shù)據(jù)庫優(yōu)化技巧


內(nèi)容整理于網(wǎng)絡(luò)

一败潦、EXPLAIN

做MySQL優(yōu)化拍谐,我們要善用 EXPLAIN 查看SQL執(zhí)行計劃峦阁。

EXPLAIN 輸出格式

EXPLAIN 命令的輸出內(nèi)容大致如下:

mysql root@localhost:youdi_auth> explain select * from  auth_user\G;
***************************[ 1. row ]***************************
id            | 1
select_type   | SIMPLE
table         | auth_user
partitions    | <null>
type          | ALL
possible_keys | <null>
key           | <null>
key_len       | <null>
ref           | <null>
rows          | 19
filtered      | 100.0
Extra         | <null>
1 row in set
Time: 0.008s

各列的含義如下:

  • id: SELECT 查詢的標(biāo)識符. 每個 SELECT 都會自動分配一個唯一的標(biāo)識符.
  • select_type: SELECT 查詢的類型.
  • table: 查詢的是哪個表
  • partitions: 匹配的分區(qū)
  • type: join 類型
  • possible_keys: 此次查詢中可能選用的索引
  • key: 此次查詢中確切使用到的索引.
  • ref: 哪個字段或常數(shù)與 key 一起被使用
  • rows: 顯示此查詢一共掃描了多少行. 這個是一個估計值.
  • filtered: 表示此查詢條件所過濾的數(shù)據(jù)的百分比
  • extra: 額外的信息

接下來我們來重點(diǎn)看一下比較重要的幾個字段.

select_type

select_type 表示了查詢的類型, 它的常用取值有:

  • SIMPLE, 表示此查詢不包含 UNION 查詢或子查詢
  • PRIMARY, 表示此查詢是最外層的查詢
  • UNION, 表示此查詢是 UNION 的第二或隨后的查詢
  • DEPENDENT UNION, UNION 中的第二個或后面的查詢語句, 取決于外面的查詢
  • UNION RESULT, UNION 的結(jié)果
  • SUBQUERY, 子查詢中的第一個 SELECT
  • DEPENDENT SUBQUERY: 子查詢中的第一個 SELECT, 取決于外面的查詢. 即子查詢依賴于外層查詢的結(jié)果.

最常見的查詢類別應(yīng)該是 SIMPLE 了, 比如當(dāng)我們的查詢沒有子查詢, 也沒有 UNION 查詢時, 那么通常就是 SIMPLE 類型, 例如:

mysql root@localhost:youdi_auth> explain select * from  auth_user where id = 396\G
***************************[ 1. row ]***************************
id            | 1
select_type   | SIMPLE
table         | auth_user
partitions    | <null>
type          | const
possible_keys | PRIMARY
key           | PRIMARY
key_len       | 4
ref           | const
rows          | 1
filtered      | 100.0
Extra         | <null>
1 row in set
Time: 0.008s

如果我們使用了 UNION 查詢, 那么 EXPLAIN 輸出 的結(jié)果類似如下:

mysql root@localhost:youdi_auth> explain (select * from  auth_user where id in (1,2,3,4)) UNION (select * from auth_user where id in (4,5,6,7,8))\G
***************************[ 1. row ]***************************
id            | 1
select_type   | PRIMARY
table         | auth_user
partitions    | <null>
type          | range
possible_keys | PRIMARY
key           | PRIMARY
key_len       | 4
ref           | <null>
rows          | 4
filtered      | 100.0
Extra         | Using where
***************************[ 2. row ]***************************
id            | 2
select_type   | UNION
table         | auth_user
partitions    | <null>
type          | range
possible_keys | PRIMARY
key           | PRIMARY
key_len       | 4
ref           | <null>
rows          | 5
filtered      | 100.0
Extra         | Using where
***************************[ 3. row ]***************************
id            | <null>
select_type   | UNION RESULT
table         | <union1,2>
partitions    | <null>
type          | ALL
possible_keys | <null>
key           | <null>
key_len       | <null>
ref           | <null>
rows          | <null>
filtered      | <null>
Extra         | Using temporary
3 rows in set
Time: 0.009s

table

表示查詢涉及的表或衍生表

type

type 字段比較重要, 它提供了判斷查詢是否高效的重要依據(jù)依據(jù). 通過 type 字段, 我們判斷此次查詢是 全表掃描 還是 索引掃描等.

type 常用類型

type 常用的取值有:

  • system: 表中只有一條數(shù)據(jù). 這個類型是特殊的 const 類型.
  • const: 針對主鍵或唯一索引的等值查詢掃描, 最多只返回一行數(shù)據(jù). const 查詢速度非成荩快, 因?yàn)樗鼉H僅讀取一次即可.
    例如下面的這個查詢, 它使用了主鍵索引, 因此 type 就是 const 類型的.
mysql root@localhost:youdi_auth> explain select * from  auth_user where id = 394\G
***************************[ 1. row ]***************************
id            | 1
select_type   | SIMPLE
table         | auth_user
partitions    | <null>
type          | const
possible_keys | PRIMARY
key           | PRIMARY
key_len       | 4
ref           | const
rows          | 1
filtered      | 100.0
Extra         | <null>
1 row in set
Time: 0.008s
  • eq_ref: 此類型通常出現(xiàn)在多表的 join 查詢, 表示對于前表的每一個結(jié)果, 都只能匹配到后表的一行結(jié)果. 并且查詢的比較操作通常是 =, 查詢效率較高. 例如:
mysql root@localhost:youmi_auth> explain select * from auth_user,auth_user_groups where auth_user.id = auth_user_groups.user_id\G
***************************[ 1. row ]***************************
id            | 1
select_type   | SIMPLE
table         | auth_user_groups
partitions    | <null>
type          | index
possible_keys | user_group_id
key           | user_group_id
key_len       | 8
ref           | <null>
rows          | 2
filtered      | 100.0
Extra         | Using index
***************************[ 2. row ]***************************
id            | 1
select_type   | SIMPLE
table         | auth_user
partitions    | <null>
type          | eq_ref
possible_keys | PRIMARY
key           | PRIMARY
key_len       | 4
ref           | youdi_auth.auth_user_groups.user_id
rows          | 1
filtered      | 100.0
Extra         | <null>
2 rows in set
Time: 0.008s
  • ref: 此類型通常出現(xiàn)在多表的 join 查詢, 針對于非唯一或非主鍵索引, 或者是使用了 最左前綴 規(guī)則索引的查詢.
    例如下面這個例子中, 就使用到了 ref 類型的查詢:
mysql root@localhost:youdi_auth> explain select * from auth_user,auth_user_groups where auth_user.id = auth_user_groups.user_id and auth_user.id = 6\G
***************************[ 1. row ]***************************
id            | 1
select_type   | SIMPLE
table         | auth_user
partitions    | <null>
type          | const
possible_keys | PRIMARY
key           | PRIMARY
key_len       | 4
ref           | const
rows          | 1
filtered      | 100.0
Extra         | <null>
***************************[ 2. row ]***************************
id            | 1
select_type   | SIMPLE
table         | auth_user_groups
partitions    | <null>
type          | ref
possible_keys | user_group_id
key           | user_group_id
key_len       | 4
ref           | const
rows          | 2
filtered      | 100.0
Extra         | Using index
2 rows in set
Time: 0.008s
  • range: 表示使用索引范圍查詢, 通過索引字段范圍獲取表中部分?jǐn)?shù)據(jù)記錄. 這個類型通常出現(xiàn)在 =, <>, >, >=, <, <=, IS NULL, <=>, BETWEEN, IN() 操作中.
    當(dāng) typerange 時, 那么 EXPLAIN 輸出的 ref 字段為 NULL, 并且 key_len 字段是此次查詢中使用到的索引的最長的那個.

例如下面的例子就是一個范圍查詢:

mysql root@localhost:youmi_auth> explain select * from  auth_user where id between 2 and 400\G
***************************[ 1. row ]***************************
id            | 1
select_type   | SIMPLE
table         | auth_user
partitions    | <null>
type          | range
possible_keys | PRIMARY
key           | PRIMARY
key_len       | 4
ref           | <null>
rows          | 18
filtered      | 100.0
Extra         | Using where
1 row in set
Time: 0.008s
  • index: 表示全索引掃描(full index scan), 和 ALL 類型類似, 只不過 ALL 類型是全表掃描, 而 index 類型則僅僅掃描所有的索引, 而不掃描數(shù)據(jù).
    index 類型通常出現(xiàn)在: 所要查詢的數(shù)據(jù)直接在索引樹中就可以獲取到, 而不需要掃描數(shù)據(jù). 當(dāng)是這種情況時, Extra 字段 會顯示 Using index.

例如:

mysql root@localhost:youdi_auth> explain select name from  auth_user\G
***************************[ 1. row ]***************************
id            | 1
select_type   | SIMPLE
table         | auth_user
partitions    | <null>
type          | ALL
possible_keys | <null>
key           | <null>
key_len       | <null>
ref           | <null>
rows          | 19
filtered      | 100.0
Extra         | <null>
1 row in set
Time: 0.008s

上面的例子中, 我們查詢的 name 字段恰好是一個索引, 因此我們直接從索引中獲取數(shù)據(jù)就可以滿足查詢的需求了, 而不需要查詢表中的數(shù)據(jù). 因此這樣的情況下, type 的值是 index, 并且 Extra 的值是 Using index.

  • ALL: 表示全表掃描, 這個類型的查詢是性能最差的查詢之一. 通常來說, 我們的查詢不應(yīng)該出現(xiàn) ALL 類型的查詢, 因?yàn)檫@樣的查詢在數(shù)據(jù)量大的情況下, 對數(shù)據(jù)庫的性能是巨大的災(zāi)難. 如一個查詢是 ALL 類型查詢, 那么一般來說可以對相應(yīng)的字段添加索引來避免.
    下面是一個全表掃描的例子, 可以看到, 在全表掃描時, possible_keys 和 key 字段都是 NULL, 表示沒有使用到索引, 并且 rows 十分巨大, 因此整個查詢效率是十分低下的.
mysql root@localhost:youdi_auth> explain select name from  auth_user where name='liangchangyou'\G
***************************[ 1. row ]***************************
id            | 1
select_type   | SIMPLE
table         | auth_user
partitions    | <null>
type          | ALL
possible_keys | <null>
key           | <null>
key_len       | <null>
ref           | <null>
rows          | 19
filtered      | 10.0
Extra         | Using where
1 row in set
Time: 0.008s

type 類型的性能比較

通常來說, 不同的 type 類型的性能關(guān)系如下:
ALL < index < range ~ index_merge < ref < eq_ref < const < system
ALL 類型因?yàn)槭侨頀呙? 因此在相同的查詢條件下, 它是速度最慢的.
index 類型的查詢雖然不是全表掃描, 但是它掃描了所有的索引, 因此比 ALL 類型的稍快.
后面的幾種類型都是利用了索引來查詢數(shù)據(jù), 因此可以過濾部分或大部分?jǐn)?shù)據(jù), 因此查詢效率就比較高了.

possible_keys

possible_keys 表示 MySQL 在查詢時, 能夠使用到的索引. 注意, 即使有些索引在 possible_keys 中出現(xiàn), 但是并不表示此索引會真正地被 MySQL 使用到. MySQL 在查詢時具體使用了哪些索引, 由 key 字段決定.

key

此字段是 MySQL 在當(dāng)前查詢時所真正使用到的索引.

key_len

表示查詢優(yōu)化器使用了索引的字節(jié)數(shù). 這個字段可以評估組合索引是否完全被使用, 或只有最左部分字段被使用到.
key_len 的計算規(guī)則如下:

  • 字符串
    • char(n): n 字節(jié)長度
    • varchar(n): 如果是 utf8 編碼, 則是 3 *n + 2字節(jié); 如果是 utf8mb4 編碼, 則是 4 *n + 2 字節(jié).
  • 數(shù)值類型:
    • TINYINT: 1字節(jié)
    • SMALLINT: 2字節(jié)
    • MEDIUMINT: 3字節(jié)
    • INT: 4字節(jié)
    • BIGINT: 8字節(jié)
  • 時間類型
    • DATE: 3字節(jié)
    • TIMESTAMP: 4字節(jié)
    • DATETIME: 8字節(jié)
  • 字段屬性: NULL 屬性 占用一個字節(jié). 如果一個字段是 NOT NULL 的, 則沒有此屬性.

我們來舉兩個簡單的栗子:

mysql root@localhost:youmi_auth> explain select * from auth_user where id > 10 and name = 'liangchangyou' and status = 0\G
***************************[ 1. row ]***************************
id            | 1
select_type   | SIMPLE
table         | auth_user
partitions    | <null>
type          | range
possible_keys | PRIMARY,id-name-status
key           | PRIMARY
key_len       | 4
ref           | <null>
rows          | 12
filtered      | 5.26
Extra         | Using where
1 row in set
Time: 0.007s

上面的例子是從表 order_info 中查詢指定的內(nèi)容, 而我們從此表的建表語句中可以知道, 表 order_info 有一個聯(lián)合索引:

 index `id-name-status` (`id`, `name`, `status`);

不過此查詢語句 where id > 10 and name = 'liangchangyou' and status = 0\G 中, 因?yàn)橄冗M(jìn)行 id 的范圍查詢, 而根據(jù) 最左前綴匹配 原則, 當(dāng)遇到范圍查詢時, 就停止索引的匹配, 因此實(shí)際上我們使用到的索引的字段只有 id,

上面因?yàn)?最左前綴匹配 原則, 我們的查詢僅僅使用到了聯(lián)合索引的 id 字段, 因此效率不算高

rows

rows 也是一個重要的字段. MySQL 查詢優(yōu)化器根據(jù)統(tǒng)計信息, 估算 SQL 要查找到結(jié)果集需要掃描讀取的數(shù)據(jù)行數(shù).
這個值非常直觀顯示 SQL 的效率好壞, 原則上 rows 越少越好.

Extra

EXplain 中的很多額外的信息會在 Extra 字段顯示, 常見的有以下幾種內(nèi)容:

  • Using filesort
    當(dāng) Extra 中有 Using filesort 時, 表示 MySQL 需額外的排序操作, 不能通過索引順序達(dá)到排序效果. 一般有 Using filesort, 都建議優(yōu)化去掉, 因?yàn)檫@樣的查詢 CPU 資源消耗大.
  • Using index
    "覆蓋索引掃描", 表示查詢在索引樹中就可查找所需數(shù)據(jù), 不用掃描表數(shù)據(jù)文件, 往往說明性能不錯
  • Using temporary
    查詢有使用臨時表, 一般出現(xiàn)于排序, 分組和多表 join 的情況, 查詢效率不高, 建議優(yōu)化.

二塌西、SQL語句中IN包含的值不應(yīng)過多

MySQL對于IN做了相應(yīng)的優(yōu)化谐宙,即將IN中的常量全部存儲在一個數(shù)組里面烫葬,而且這個數(shù)組是排好序的。但是如果數(shù)值較多,產(chǎn)生的消耗也是比較大的搭综。再例如:select id from t where num in(1,2,3) 對于連續(xù)的數(shù)值垢箕,能用 between 就不要用 in 了;再或者使用連接來替換兑巾。

三条获、SELECT語句務(wù)必指明字段名稱

SELECT *增加很多不必要的消耗(cpu、io蒋歌、內(nèi)存帅掘、網(wǎng)絡(luò)帶寬);增加了使用覆蓋索引的可能性堂油;當(dāng)表結(jié)構(gòu)發(fā)生改變時修档,前斷也需要更新。所以要求直接在select后面接上字段名府框。

四吱窝、當(dāng)只需要一條數(shù)據(jù)的時候,使用limit 1

這是為了使EXPLAIN中type列達(dá)到const類型

五迫靖、如果排序字段沒有用到索引院峡,就盡量少排序

六、如果限制條件中其他字段沒有索引系宜,盡量少用or

or兩邊的字段中照激,如果有一個不是索引字段,而其他條件也不是索引字段盹牧,會造成該查詢不走索引的情況俩垃。很多時候使用 union all 或者是union(必要的時候)的方式來代替“or”會得到更好的效果

七、盡量用union all代替union

union和union all的差異主要是前者需要將結(jié)果集合并后再進(jìn)行唯一性過濾操作欢策,這就會涉及到排序吆寨,增加大量的CPU運(yùn)算,加大資源消耗及延遲踩寇。當(dāng)然啄清,union all的前提條件是兩個結(jié)果集沒有重復(fù)數(shù)據(jù)。

八俺孙、不使用ORDER BY RAND()

select id from `dynamic` order by rand() limit 1000;

上面的sql語句辣卒,可優(yōu)化為

select id from `dynamic` t1 join (select rand() * (select max(id) from `dynamic`) as nid) t2 on t1.id > t2.nid limit 1000;

九、區(qū)分in和exists睛榄, not in和not exists

select * from 表A where id in (select id from 表B)

上面sql語句相當(dāng)于

select * from 表A where exists(select * from 表B where 表B.id=表A.id)

區(qū)分in和exists主要是造成了驅(qū)動順序的改變(這是性能變化的關(guān)鍵)荣茫,如果是exists,那么以外層表為驅(qū)動表场靴,先被訪問啡莉,如果是IN港准,那么先執(zhí)行子查詢。所以IN適合于外表大而內(nèi)表小的情況咧欣;EXISTS適合于外表小而內(nèi)表大的情況浅缸。關(guān)于not in和not exists,推薦使用not exists魄咕,不僅僅是效率問題衩椒,not in可能存在邏輯問題。如何高效的寫出一個替代not exists的sql語句哮兰?

原sql語句

select colname … from A表 where a.id not in (select b.id from B表)

高效的sql語句

select colname … from A表 Left join B表 on where a.id = b.id where b.id is null

取出的結(jié)果集如下圖表示毛萌,A表不在B表中的數(shù)據(jù)

十、使用合理的分頁方式以提高分頁的效率

select id,name from product limit 866613, 20

使用上述sql語句做分頁的時候喝滞,可能有人會發(fā)現(xiàn)阁将,隨著表數(shù)據(jù)量的增加,直接使用limit分頁查詢會越來越慢右遭。

優(yōu)化的方法如下:可以取前一頁的最大行數(shù)的id冀痕,然后根據(jù)這個最大的id來限制下一頁的起點(diǎn)。比如此列中狸演,上一頁最大的id是866612。sql可以采用如下的寫法:

select id,name from product where id> 866612 limit 20

十一僻他、分段查詢

在一些用戶選擇頁面中宵距,可能一些用戶選擇的時間范圍過大,造成查詢緩慢吨拗。主要的原因是掃描行數(shù)過多满哪。這個時候可以通過程序,分段進(jìn)行查詢劝篷,循環(huán)遍歷哨鸭,將結(jié)果合并處理進(jìn)行展示。

掃描的行數(shù)成百萬級以上的時候就可以使用分段查詢

十二娇妓、避免在 where 子句中對字段進(jìn)行 null 值判斷

對于null的判斷會導(dǎo)致引擎放棄使用索引而進(jìn)行全表掃描像鸡。

十三、不建議使用%前綴模糊查詢

例如LIKE “%name”或者LIKE “%name%”哈恰,這種查詢會導(dǎo)致索引失效而進(jìn)行全表掃描只估。但是可以使用LIKE “name%”。

那如何查詢%name%着绷?

雖然給字段添加了索引蛔钙,但在explain結(jié)果果并沒有使用


那么如何解決這個問題呢,答案:使用全文索引

在我們查詢中經(jīng)常會用到select id,fnum,fdst from dynamic_201606 where user_name like '%zhangsan%'; 荠医。這樣的語句吁脱,普通索引是無法滿足查詢需求的桑涎。慶幸的是在MySQL中,有全文索引來幫助我們兼贡。

創(chuàng)建全文索引的sql語法是:

ALTER TABLE `dynamic_201606` ADD FULLTEXT INDEX `idx_user_name` (`user_name`);

使用全文索引的sql語句是:

select id,fnum,fdst from dynamic_201606 where match(user_name) against('zhangsan' in boolean mode);

注意:在需要創(chuàng)建全文索引之前攻冷,請聯(lián)系DBA確定能否創(chuàng)建。同時需要注意的是查詢語句的寫法與普通索引的區(qū)別

十四紧显、避免在where子句中對字段進(jìn)行表達(dá)式操作

比如

select user_id,user_project from user_base where age*2=36;

中對字段就行了算術(shù)運(yùn)算讲衫,這會造成引擎放棄使用索引,建議改成

select user_id,user_project from user_base where age=36/2;

十五孵班、避免隱式類型轉(zhuǎn)換

where 子句中出現(xiàn) column 字段的類型和傳入的參數(shù)類型不一致的時候發(fā)生的類型轉(zhuǎn)換涉兽,建議先確定where中的參數(shù)類型


十六、對于聯(lián)合索引來說篙程,要遵守最左前綴法則

舉列來說索引含有字段id,name,school枷畏,可以直接用id字段,也可以id,name這樣的順序虱饿,但是name;school都無法使用這個索引拥诡。所以在創(chuàng)建聯(lián)合索引的時候一定要注意索引字段順序,常用的查詢字段放在最前面

十七氮发、必要時可以使用force index來強(qiáng)制查詢走某個索引

有的時候MySQL優(yōu)化器采取它認(rèn)為合適的索引來檢索sql語句渴肉,但是可能它所采用的索引并不是我們想要的。這時就可以采用force index來強(qiáng)制優(yōu)化器使用我們制定的索引爽冕。

十八仇祭、注意范圍查詢語句

對于聯(lián)合索引來說,如果存在范圍查詢颈畸,比如between,>,<等條件時乌奇,會造成后面的索引字段失效。

十九眯娱、關(guān)于JOIN優(yōu)化

  • LEFT JOIN A表為驅(qū)動表
  • INNER JOIN MySQL會自動找出那個數(shù)據(jù)少的表作用驅(qū)動表
  • RIGHT JOIN B表為驅(qū)動表

注意:MySQL中沒有full join礁苗,可以用以下方式來解決

select * from A left join B on B.name = A.name 
where B.name is null
 union all
select * from B;

盡量使用inner join,避免left join

參與聯(lián)合查詢的表至少為2張表徙缴,一般都存在大小之分试伙。如果連接方式是inner join,在沒有其他過濾條件的情況下MySQL會自動選擇小表作為驅(qū)動表娜搂,但是left join在驅(qū)動表的選擇上遵循的是左邊驅(qū)動右邊的原則迁霎,即left join左邊的表名為驅(qū)動表。

合理利用索引

被驅(qū)動表的索引字段作為on的限制字段百宇。

利用小表去驅(qū)動大表

從原理圖能夠直觀的看出如果能夠減少驅(qū)動表的話考廉,減少嵌套循環(huán)中的循環(huán)次數(shù),以減少 IO總量及CPU運(yùn)算的次數(shù)携御。

巧用STRAIGHT_JOIN

inner join是由mysql選擇驅(qū)動表昌粤,但是有些特殊情況需要選擇另個表作為驅(qū)動表既绕,比如有g(shù)roup by、order by等「Using filesort」涮坐、「Using temporary」時凄贩。STRAIGHT_JOIN來強(qiáng)制連接順序,在STRAIGHT_JOIN左邊的表名就是驅(qū)動表袱讹,右邊則是被驅(qū)動表疲扎。在使用STRAIGHT_JOIN有個前提條件是該查詢是內(nèi)連接,也就是inner join捷雕。其他鏈接不推薦使用STRAIGHT_JOIN椒丧,否則可能造成查詢結(jié)果不準(zhǔn)確。

這個方式有時可能減少3倍的時間救巷。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末壶熏,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子浦译,更是在濱河造成了極大的恐慌棒假,老刑警劉巖,帶你破解...
    沈念sama閱讀 218,036評論 6 506
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件精盅,死亡現(xiàn)場離奇詭異帽哑,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)叹俏,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,046評論 3 395
  • 文/潘曉璐 我一進(jìn)店門祝拯,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人她肯,你說我怎么就攤上這事∮ス螅” “怎么了晴氨?”我有些...
    開封第一講書人閱讀 164,411評論 0 354
  • 文/不壞的土叔 我叫張陵,是天一觀的道長碉输。 經(jīng)常有香客問我籽前,道長,這世上最難降的妖魔是什么敷钾? 我笑而不...
    開封第一講書人閱讀 58,622評論 1 293
  • 正文 為了忘掉前任枝哄,我火速辦了婚禮,結(jié)果婚禮上阻荒,老公的妹妹穿的比我還像新娘挠锥。我一直安慰自己,他們只是感情好侨赡,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,661評論 6 392
  • 文/花漫 我一把揭開白布蓖租。 她就那樣靜靜地躺著粱侣,像睡著了一般。 火紅的嫁衣襯著肌膚如雪蓖宦。 梳的紋絲不亂的頭發(fā)上齐婴,一...
    開封第一講書人閱讀 51,521評論 1 304
  • 那天,我揣著相機(jī)與錄音稠茂,去河邊找鬼柠偶。 笑死,一個胖子當(dāng)著我的面吹牛睬关,可吹牛的內(nèi)容都是我干的诱担。 我是一名探鬼主播,決...
    沈念sama閱讀 40,288評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼共螺,長吁一口氣:“原來是場噩夢啊……” “哼该肴!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起藐不,我...
    開封第一講書人閱讀 39,200評論 0 276
  • 序言:老撾萬榮一對情侶失蹤匀哄,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后雏蛮,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體涎嚼,經(jīng)...
    沈念sama閱讀 45,644評論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,837評論 3 336
  • 正文 我和宋清朗相戀三年挑秉,在試婚紗的時候發(fā)現(xiàn)自己被綠了法梯。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 39,953評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡犀概,死狀恐怖立哑,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情姻灶,我是刑警寧澤铛绰,帶...
    沈念sama閱讀 35,673評論 5 346
  • 正文 年R本政府宣布,位于F島的核電站产喉,受9級特大地震影響捂掰,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜曾沈,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,281評論 3 329
  • 文/蒙蒙 一这嚣、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧塞俱,春花似錦姐帚、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,889評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽惫皱。三九已至,卻和暖如春尤莺,著一層夾襖步出監(jiān)牢的瞬間旅敷,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,011評論 1 269
  • 我被黑心中介騙來泰國打工颤霎, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留媳谁,地道東北人。 一個月前我還...
    沈念sama閱讀 48,119評論 3 370
  • 正文 我出身青樓友酱,卻偏偏與公主長得像晴音,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子缔杉,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,901評論 2 355