Java異常處理機(jī)制

什么是異常?

  • 異常本質(zhì)上是程序上的錯誤,錯誤在我們編寫程序的過程中會經(jīng)常發(fā)生池凄,包括編譯期間和運(yùn)行期間的錯誤。
  • 編譯期間的錯誤通常是基礎(chǔ)的語法錯誤鬼廓,比如括號沒有正常配對肿仑、語句結(jié)束后少寫了分號,關(guān)鍵字編寫錯誤等碎税,編譯器會對這些錯誤給出提示尤慰,幫助我們進(jìn)行修訂。
  • 運(yùn)行期間的錯誤只有程序運(yùn)行時才能看到錯誤的提示雷蹂,比如數(shù)組訪問時下標(biāo)越界伟端、使用空對象調(diào)用方法、算術(shù)運(yùn)算時除數(shù)為0匪煌、類型轉(zhuǎn)換時無法正常轉(zhuǎn)型等荔泳,運(yùn)行期間的錯誤往往是難以預(yù)料的。
程序中的異常
  • 在程序運(yùn)行過程中虐杯,意外發(fā)生的情況玛歌,背離我們程序本身的意圖的表現(xiàn),都可以理解為異常擎椰。
  • 當(dāng)程序在運(yùn)行期間出現(xiàn)了異常支子,如果置之不理,程序可能會不正常運(yùn)行达舒、強(qiáng)制中斷運(yùn)行值朋、造成用戶數(shù)據(jù)丟失、資源無法正常釋放巩搏、直接導(dǎo)致系統(tǒng)崩潰,顯然這不是我們希望看到的結(jié)果昨登。
  • 利用Java中的異常處理機(jī)制,我們可以更好地提升程序的健壯性贯底。

異常的分類

在java中丰辣,通過Throwable以及它的相關(guān)子類來描述各種不同的異常類型。
Throwable是異常的根類禽捆,包含兩個子類ErrorException

Throwable類常用方法

String getMessage() 返回保存在某個異常中的描述字符串,異常參數(shù)調(diào)用
void printStackTrace() 顯示堆棧跟蹤信息

Error
  • Error是程序無法處理的錯誤笙什,表示運(yùn)行應(yīng)用程序中較嚴(yán)重問題。
  • 大多數(shù)的錯誤與代碼編寫所執(zhí)行的操作是沒有什么關(guān)系的胚想,而表示代碼運(yùn)行的時候java虛擬機(jī)出現(xiàn)的系列問題琐凭。
  • 常見的有虛擬機(jī)錯誤、內(nèi)存溢出浊服、線程死鎖等统屈,這些錯誤往往是不可查的胚吁,因?yàn)樗鼈冊趹?yīng)用程序的控制和處理能力之外,而且絕大多數(shù)是程序運(yùn)行時不允許出現(xiàn)的狀況愁憔。
  • 對于設(shè)計(jì)合理的應(yīng)用程序來說腕扶,即使確實(shí)發(fā)生了錯誤,本質(zhì)上也不應(yīng)該試圖去處理它所引起的異常狀況惩淳。
Exception
  • Exception是程序本身可以處理的異常。異常處理通常指的是針對這類異常的處理
  • Exception類的異常包括Unchecked ExceptionChecked Exception
  • Unchecked Exception(非檢查異常):編譯器不要求強(qiáng)制處理的異常乓搬,包含RuntimeException以及它的相關(guān)子類
  • Checked Exception(檢查異常):編譯器要求必須處理的異常思犁,除了RuntimeException以及它的相關(guān)子類其他的Exception子類都是檢查異常,如IOException进肯、SQLException
常見的異常類型

異常處理

在Java應(yīng)用程序中激蹲,異常處理機(jī)制為:拋出異常、捕獲異常

JVM默認(rèn)處理機(jī)制

JVM有一個默認(rèn)的異常處理機(jī)制江掩,即將該異常的名稱学辱、異常的信息、異常出現(xiàn)的位置打印在了控制臺上环形,同時將程序停止運(yùn)行

拋出異常
  • 當(dāng)一個方法出現(xiàn)錯誤引發(fā)異常時策泣,方法創(chuàng)建異常對象并交付運(yùn)行時系統(tǒng)進(jìn)行處理。
  • 異常對象通常包含異常類型和異常出現(xiàn)時的程序狀態(tài)等信息抬吟。
  • 運(yùn)行時系統(tǒng)負(fù)責(zé)尋找處置異常的代碼并執(zhí)行萨咕。
  • 在方法拋出異常之后,運(yùn)行時系統(tǒng)將轉(zhuǎn)為尋找合適的異常處理器火本。
  • 運(yùn)行時系統(tǒng)從發(fā)生異常的方法開始危队,依次回查調(diào)用棧中的方法,當(dāng)異常處理器所能處理的異常類型與方法拋出的異常類型相符時钙畔,即為合適的異常處理器茫陆。
  • 當(dāng)運(yùn)行時系統(tǒng)遍歷調(diào)用棧而未找到合適的異常處理器,則運(yùn)行時系統(tǒng)終止擎析。同時簿盅,意味著Java程序的終止。
捕獲異常

對于運(yùn)行時異常揍魂、錯誤或可查異常挪鹏,java技術(shù)所要求的異常處理方式有所不同。
Java規(guī)定對于可查異常必須捕獲愉烙、或者聲明拋出讨盒,而允許忽略不可查的RuntimeException(含子類)和Error(含子類)

實(shí)現(xiàn)

主要通過5個關(guān)鍵字來實(shí)現(xiàn):trycatch步责、finally返顺、throw禀苦、throws

try-catch-finally

語法格式:

try塊:用于捕獲異常
catch塊:用于處理try捕獲到的異常
finally塊:無論是否發(fā)生異常代碼總能執(zhí)行
try塊后可接零個或多個catch塊,如果沒有catch塊遂鹊,則必須跟一個finally

執(zhí)行流程
  1. 我們將可能產(chǎn)生異常的代碼放入try塊當(dāng)中振乏,當(dāng)try塊中代碼沒有異常發(fā)生時,catch塊中的內(nèi)容不會被執(zhí)行秉扑,而直接執(zhí)行之后的代碼慧邮。
  2. 當(dāng)try塊發(fā)生異常時,會產(chǎn)生一個異常對象且當(dāng)該類型能與catch塊中的異常類型正常匹配時舟陆,程序就會進(jìn)入到catch塊執(zhí)行相應(yīng)的處理邏輯误澳,然后順序執(zhí)行下去。
  3. 當(dāng)出現(xiàn)異常且無法正常匹配處理則程序中斷運(yùn)行
示例
public class TryDemo {
    public static void main(String[] args) {
        //定義兩個整數(shù)秦躯,接受用戶的鍵盤輸入忆谓,輸出兩數(shù)之商
        Scanner input=new Scanner(System.in);
        System.out.println("=====運(yùn)算開始=====");
        System.out.print("請輸入第一個整數(shù):");
        int one=input.nextInt();
        System.out.print("請輸入第二個整數(shù):");
        int two=input.nextInt();
        System.out.println("one和two的商是:"+ (one/two));
        System.out.println("=====運(yùn)算結(jié)束=====");
    }
}
程序運(yùn)行結(jié)果

當(dāng)我們輸入的是非數(shù)字時,程序會報(bào)錯并終止運(yùn)行踱承,報(bào)錯的異常為InputMismatchException
當(dāng)我們輸入的第二個數(shù)為0時倡缠,程序也會報(bào)錯并終止運(yùn)行,報(bào)錯的異常為ArithmeticException

使用try-catch-finally對異常進(jìn)行捕獲處理
public class TryDemo {
    public static void main(String[] args) {
        //定義兩個整數(shù)茎活,接受用戶的鍵盤輸入昙沦,輸出兩數(shù)之商
        Scanner input=new Scanner(System.in);
        try {
            System.out.println("=====運(yùn)算開始=====");
            System.out.print("請輸入第一個整數(shù):");
            int one=input.nextInt();
            System.out.print("請輸入第二個整數(shù):");
            int two=input.nextInt();
            System.out.println("one和two的商是:"+ (one/two));
        } catch (Exception e) {
            System.out.println("程序出錯啦~~~~");
            e.printStackTrace(); //打印錯誤的堆棧信息
        }finally{
            System.out.println("=====運(yùn)算結(jié)束=====");
        }
    }
}

此時如果發(fā)生上述任意一種錯誤時,程序會執(zhí)行catch塊中的處理邏輯载荔,然后繼續(xù)往下執(zhí)行直到程序結(jié)束桅滋;
這里catch塊中的異常類型為Exception,是所有可處理異常類的基類身辨,所以出現(xiàn)任何類型異常都能匹配上丐谋;
而定義在finally塊中的邏輯一定會被執(zhí)行,不管程序是否出現(xiàn)異常煌珊。

嵌套try-catch塊

如果內(nèi)部try代碼塊產(chǎn)生的異常沒有被與該try對應(yīng)的catch捕獲号俐,會傳到外部try代碼塊。
使用外部try捕獲大部分嚴(yán)重錯誤的同時定庵,讓內(nèi)部try代碼塊處理不太嚴(yán)重的錯誤吏饿。

使用多重catch結(jié)構(gòu)處理異常

當(dāng)程序可能會產(chǎn)生多種類型的異常,針對可能出現(xiàn)的不同異常如果希望做不同的處理蔬浙,那么就可以使用多重catch
注意多重catch塊中的異常類型不能一致猪落,且捕獲父類型的catch塊應(yīng)該在子類型的后面,比如Exception應(yīng)該在最后面

注意事項(xiàng)
  1. 一旦某個catch捕獲到匹配的異常類型畴博,將進(jìn)入異常處理代碼笨忌。一經(jīng)處理結(jié)束,就意味著整個try-catch語句結(jié)束俱病,其他的catch子句不再有匹配和捕獲異常類型的機(jī)會官疲。
  2. 對于有多個catch子句的異常程序而言袱结,應(yīng)該盡量將捕獲底層異常類的catch子句放在前面,同時盡量將捕獲相對高層的異常類的catch子句放在后面途凫。否則,捕獲底層異常類的catch子句將可能會被屏蔽垢夹。
示例
public class TryDemo {
    public static void main(String[] args) {
        //定義兩個整數(shù),接受用戶的鍵盤輸入维费,輸出兩數(shù)之商
        Scanner input=new Scanner(System.in);
        try{
            System.out.print("請輸入第一個整數(shù):");
            int one=input.nextInt();
            System.out.print("請輸入第二個整數(shù):");
            int two=input.nextInt();
            System.out.println("one和two的商是:"+ (one/two));
        }catch(ArithmeticException e){
            System.exit(1);
            System.out.println("除數(shù)不允許為零");
            e.printStackTrace();
        }catch(InputMismatchException e){
            System.out.println("請輸入整數(shù)");
            e.printStackTrace();
        }catch(Exception e){ //位置應(yīng)該在最后一個catch塊中
            //如果出現(xiàn)的異常沒有被前面的catch塊匹配果元,那么在此處進(jìn)行處理
            System.out.println("出錯啦~~");
            e.printStackTrace();
        }finally{
            System.out.println("=====運(yùn)算結(jié)束=====");
        }
    }
}
終止finally執(zhí)行的方法

上面的程序如果第二個輸入的數(shù)字為0的話,那么程序就終止了犀盟,沒有任何打印輸出而晒。因?yàn)楫?dāng)執(zhí)行System.exit(1)方法就表示程序無條件終止運(yùn)行,后面的finally也就不會被執(zhí)行

return的說明

當(dāng)代碼中出現(xiàn)return時且蓬,一定是finally語句塊執(zhí)行完成后才會去執(zhí)行相應(yīng)的return代碼欣硼,無論return語句在什么位置题翰。


示例:

public class TryDemo {
    public static void main(String[] args) {
        int result=test();
        System.out.println("one和two的商是:"+ result);
        
    }
    public static int test(){
        Scanner input=new Scanner(System.in);
        System.out.println("=====運(yùn)算開始=====");
        try{
            System.out.print("請輸入第一個整數(shù):");
            int one=input.nextInt();
            System.out.print("請輸入第二個整數(shù):");
            int two=input.nextInt();
            return one/two;
        }catch(ArithmeticException e){
            System.out.println("除數(shù)不允許為零");
            return 0;
        }finally{
            System.out.println("=====運(yùn)算結(jié)束=====");
            return -100000; //最好不要在finally語句中返回方法結(jié)果
        }
    }
}
運(yùn)行結(jié)果

當(dāng)輸入的兩個數(shù)為36和6時恶阴,程序的執(zhí)行結(jié)果為:one和two的商是:-10000
當(dāng)輸入的兩個數(shù)為36和0時,程序的執(zhí)行結(jié)果為:one和two的商是:-10000
所以當(dāng)try/catchfinally同時存在return語句返回方法值時豹障,無論程序是否正常執(zhí)行冯事,最終返回的都是finally的結(jié)果

throw和throws

可以通過throws聲明將要拋出何種類型的異常,通過throw將產(chǎn)生的異常拋出

throws

throws語句用在方法定義時聲明該方法要拋出的異常類型
如果一個方法可能會出現(xiàn)異常血公,但不想或者沒有能力處理這種異常昵仅,可以在方法聲明處用throws子句來聲明拋出異常
當(dāng)方法拋出異常時,方法將不對這些類型及其子類類型的異常作處理累魔,而拋向調(diào)用該方法的方法摔笤,由他去處理

使用規(guī)則
  1. 如果是不可查異常(unchecked exception),即Error垦写、RuntimeException或它們的子類吕世,那么可以不使用throws關(guān)鍵字來聲明要拋出的異常,編譯仍能順利通過梯投,但在運(yùn)行時會被系統(tǒng)拋出
  2. 如果一個方法中可能出現(xiàn)可查異常命辖,要么用try-catch語句捕獲,要么用throws子句聲明將它拋出分蓖,否則編譯出錯
  3. 當(dāng)拋出了檢查異常時尔艇,則該方法的調(diào)用者必須處理或者重新拋出該異常
  4. 當(dāng)子類重寫父類拋出異常的方法時,聲明的異常必須是父類方法所聲明異常的同類或子類
通過throws拋出異常的解決方案

1.throws后面接多個異常類型么鹤,中間用逗號分隔
2.throws后面接Exception终娃,表示任何異常都向外拋出

注意事項(xiàng)

根據(jù)throws拋出的異常類型來決定調(diào)用者是否必須處理該異常,如果是非檢查異常則可以不處理蒸甜,而如果是檢查異常尝抖,則必須捕獲處理毡们,而Exception也包含了非檢查異常,所以也必須進(jìn)行處理昧辽。
對于方法只拋出非檢查異常我們可以通過文檔注釋來標(biāo)識方法拋出的異常衙熔,這樣對調(diào)用者更友好。

示例
import java.util.InputMismatchException;
import java.util.Scanner;

public class TryDemo {
    public static void main(String[] args) {
        //在Eclipse中可以選中代碼通過右鍵Surround With -> Try/Catch Block完成處理異常的代碼
        //方案一:針對方法拋出的多個異常進(jìn)行捕獲處理,此時可以只選擇捕獲處理其中一個異常
        try {
            int result=test();
            System.out.println("one和two的商是:"+ result);
        } catch (ArithmeticException e) {
            System.out.println("除數(shù)不允許為零");
            e.printStackTrace();
        } catch (InputMismatchException e){
            System.out.println("請輸入整數(shù)");
            e.printStackTrace();
        }
        //方案二:如果方法拋出的是Exception類型搅荞,那么catch塊中必須包含對Exception的處理红氯,其他子類異常處理是可選的
        try{
            int result = test2();
            System.out.println("one和two的商是:" + result);
        }catch(ArithmeticException e){
            
        }catch(InputMismatchException e){
            
        }catch(Exception e){//這個catch塊必須包含
            
        }
    }

    //方案一:throws后面接多個異常類型,中間用逗號分隔
    /**
     * 使用文檔注釋給出異常提示
     * @return
     * @throws ArithmeticException
     * @throws InputMismatchException
     */
    public static int test() throws ArithmeticException, InputMismatchException{
        Scanner input=new Scanner(System.in);
        System.out.println("=====運(yùn)算開始=====");
        System.out.print("請輸入第一個整數(shù):");
        int one=input.nextInt();
        System.out.print("請輸入第二個整數(shù):");
        int two=input.nextInt();
        System.out.println("=====運(yùn)算結(jié)束=====");
        return one / two;
    }
    //方案二:throws后面接Exception咕痛,表示任何異常都向外拋出
    public static int test2() throws Exception{
        Scanner input=new Scanner(System.in);
        System.out.println("=====運(yùn)算開始=====");
        System.out.print("請輸入第一個整數(shù):");
        int one=input.nextInt();
        System.out.print("請輸入第二個整數(shù):");
        int two=input.nextInt();
        System.out.println("=====運(yùn)算結(jié)束=====");
        return one / two;
    }
}

throw

throw用來拋出一個異常痢甘,例如:throw new IOException();
throw拋出的只能夠是可拋出類Throwable或者其子類的實(shí)例對象。如:throw new String("出錯了");是錯誤的

throw拋出異常對象的處理方案

1.在throw語句外面套上try-catch塊茉贡,自己拋出的異常自己處理
2.通過throws在方法聲明處拋出異常類型塞栅,誰調(diào)用方法誰處理,調(diào)用者可以自己處理腔丧,也可以繼續(xù)上拋放椰,此時可以拋出與throw對象相同的類型或者其父類

異常拋出與處理作用
  1. 規(guī)避可能出現(xiàn)的風(fēng)險(xiǎn)
  2. 完成一些程序的邏輯

示例:完成酒店入住限定的場景

public class TryDemo {
    public static void main(String[] args) {
        try {
            testAge(); 
        }catch(Exception e){
            //當(dāng)發(fā)生異常時打印:java.lang.Exception: 18歲以下愉粤,80歲以上的住客必須由親友陪同
            e.printStackTrace();
        }
    }
    // 描述酒店的入住規(guī)則:限定年齡砾医,18歲以下,80歲以上的住客必須由親友陪同
    public static void testAge() {
        try {
            System.out.println("請輸入年齡:");
            Scanner input = new Scanner(System.in);
            int age = input.nextInt();
            if (age < 18 || age > 80) {
                throw new Exception("18歲以下衣厘,80歲以上的住客必須由親友陪同");
            } else {
                System.out.println("歡迎入住本酒店");
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

自定義異常

  • 使用Java內(nèi)置的異常類可以描述在編程時出現(xiàn)的大部分異常情況如蚜。
  • 也可以通過自定義異常描述特定業(yè)務(wù)產(chǎn)生的異常類型。
  • 所謂自定義異常影暴,就是定義一個類错邦,去繼承Throwable類或者它的子類。

示例:我們用自定義異常去描述不滿足酒店入住規(guī)則的情況

/**
 * 自定義異常
 */
public class HotelAgeException extends Exception {
    public HotelAgeException(){
        super("18歲以下型宙,80歲以上的住客必須由親友陪同");
    }
}
//測試類
public class TryDemo {
    public static void main(String[] args) {
        try {
            testAge(); 
        } catch (HotelAgeException e) {
            System.out.println(e.getMessage()); //18歲以下撬呢,80歲以上的住客必須由親友陪同
            System.out.println("酒店前臺工作人員不允許辦理入住登記");
        }catch(Exception e){
            e.printStackTrace();
        }
    }
    // 描述酒店的入住規(guī)則:限定年齡,18歲以下早歇,80歲以上的住客必須由親友陪同
    public static void testAge() throws HotelAgeException {
        System.out.println("請輸入年齡:");
        Scanner input = new Scanner(System.in);
        int age = input.nextInt();
        if (age < 18 || age > 80) {
            throw new HotelAgeException(); //拋出自定義異常
        } else {
            System.out.println("歡迎入住本酒店");
        }
    }
}

異常鏈

有時候我們會捕獲一個異常后再拋出另一個異常倾芝。此時異常會如何顯示呢?

示例:有三個方法testOne箭跳、testTwo晨另、testThree,依次進(jìn)行調(diào)用捕獲異常并拋出一個新的異常

public class TryDemo {

    public static void main(String[] args) {
        try {
            testThree();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    public static void testOne() throws HotelAgeException {
        throw new HotelAgeException();
    }

    public static void testTwo() throws Exception {
        try {
            testOne();
        } catch (HotelAgeException e) {
            throw new Exception("我是新產(chǎn)生的異常1");
        }
    }

    public static void testThree() throws Exception {
        try {
            testTwo();
        } catch (Exception e) {
            throw new Exception("我是新產(chǎn)生的異常2");
        }
    }
}
運(yùn)行結(jié)果

只顯示了最后拋出的異常2谱姓,前面兩個方法的異常信息是丟失的借尿,這就是一種由于新拋出異常導(dǎo)致異常信息丟失的場景,如何將前面的異常信息也保留下來呢,java就提供了這種保留異常信息的機(jī)制路翻。


解決方案
  1. 可以通過構(gòu)造方法將異常對象作為參數(shù)去構(gòu)造新的異常對象
  2. 調(diào)用Throwable提供的initCause方法

修改代碼:

    public static void testTwo() throws Exception {
        try {
            testOne();
        } catch (HotelAgeException e) {
            //通過構(gòu)造方法保留異常信息
            throw new Exception("我是新產(chǎn)生的異常1", e);
        }
    }

    public static void testThree() throws Exception {
        try {
            testTwo();
        } catch (Exception e) {
            Exception e1=new Exception("我是新產(chǎn)生的異常2");
            //通過initCause方法保留異常信息
            e1.initCause(e);
            throw e1;
//          throw new Exception("我是新產(chǎn)生的異常2",e);
        }
    }
}

運(yùn)行結(jié)果:

異常鏈

當(dāng)捕獲一個異常后再拋出另一個異常時狈癞,如果希望將異常發(fā)生的原因一個傳一個串起來,即把底層的異常信息傳給上層,這樣逐層拋出而形成的一種鏈條

Java異常處理的優(yōu)點(diǎn)

  1. 把異常情況表現(xiàn)成異常類茂契,可以充分發(fā)揮類的可擴(kuò)展和可重用的優(yōu)勢
  2. 異常流程代碼和正常流程的代碼分離蝶桶,提高了程序的可讀性,簡化了程序的結(jié)構(gòu)
  3. 可以靈活的處理異常掉冶,有能力處理就捕獲并處理真竖,否則就拋出異常,由方法調(diào)用者處理它

經(jīng)驗(yàn)與總結(jié)

  • 處理運(yùn)行時異常時厌小,采用邏輯去合理規(guī)避同時輔助try-catch處理
  • 在多重catch塊后面,可以加一個catch(Exception)來處理可能會被遺漏的異常
  • 對于不確定的代碼恢共,也可以加上try-catch,處理潛在的異常
  • 盡量去處理異常璧亚,切忌只是簡單的調(diào)用printStackTrace()去打印輸出
  • 具體如何處理異常讨韭,要根據(jù)不同的業(yè)務(wù)需求和異常類型去決定
  • 盡量添加finally語句塊去釋放占用的資源
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市癣蟋,隨后出現(xiàn)的幾起案子透硝,更是在濱河造成了極大的恐慌,老刑警劉巖梢薪,帶你破解...
    沈念sama閱讀 221,695評論 6 515
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件蹬铺,死亡現(xiàn)場離奇詭異尝哆,居然都是意外死亡秉撇,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,569評論 3 399
  • 文/潘曉璐 我一進(jìn)店門秋泄,熙熙樓的掌柜王于貴愁眉苦臉地迎上來琐馆,“玉大人,你說我怎么就攤上這事恒序∈蒴铮” “怎么了?”我有些...
    開封第一講書人閱讀 168,130評論 0 360
  • 文/不壞的土叔 我叫張陵歧胁,是天一觀的道長滋饲。 經(jīng)常有香客問我,道長喊巍,這世上最難降的妖魔是什么屠缭? 我笑而不...
    開封第一講書人閱讀 59,648評論 1 297
  • 正文 為了忘掉前任,我火速辦了婚禮崭参,結(jié)果婚禮上呵曹,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好奄喂,可當(dāng)我...
    茶點(diǎn)故事閱讀 68,655評論 6 397
  • 文/花漫 我一把揭開白布铐殃。 她就那樣靜靜地躺著,像睡著了一般跨新。 火紅的嫁衣襯著肌膚如雪富腊。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 52,268評論 1 309
  • 那天域帐,我揣著相機(jī)與錄音蟹肘,去河邊找鬼。 笑死俯树,一個胖子當(dāng)著我的面吹牛帘腹,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播许饿,決...
    沈念sama閱讀 40,835評論 3 421
  • 文/蒼蘭香墨 我猛地睜開眼阳欲,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了陋率?” 一聲冷哼從身側(cè)響起球化,我...
    開封第一講書人閱讀 39,740評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎瓦糟,沒想到半個月后筒愚,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 46,286評論 1 318
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡菩浙,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 38,375評論 3 340
  • 正文 我和宋清朗相戀三年巢掺,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片劲蜻。...
    茶點(diǎn)故事閱讀 40,505評論 1 352
  • 序言:一個原本活蹦亂跳的男人離奇死亡陆淀,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出先嬉,到底是詐尸還是另有隱情轧苫,我是刑警寧澤,帶...
    沈念sama閱讀 36,185評論 5 350
  • 正文 年R本政府宣布疫蔓,位于F島的核電站含懊,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏衅胀。R本人自食惡果不足惜岔乔,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,873評論 3 333
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望拗小。 院中可真熱鬧重罪,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,357評論 0 24
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至呼胚,卻和暖如春茄唐,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背蝇更。 一陣腳步聲響...
    開封第一講書人閱讀 33,466評論 1 272
  • 我被黑心中介騙來泰國打工沪编, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人年扩。 一個月前我還...
    沈念sama閱讀 48,921評論 3 376
  • 正文 我出身青樓蚁廓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親厨幻。 傳聞我的和親對象是個殘疾皇子相嵌,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,515評論 2 359