2013/12/10

[Android] Bundle Error: java.lang.NullPointerException

使用Eclipse編寫Android程式,撰寫兩個Activity以上之間的切換,常常Activity之間會需要有資料的傳遞,就必須要透過Intent()及Bundle()來完成。

Android的資料傳遞架構如下



Activity 1透過Intent()的setClass(Activity 1, Activity 2) method轉換到Activity 2,然後同時Activity 1利用putString(key, value)把資料放進Bundle()裡,然後putExtras()到Intent(),傳遞到Activity 2。當Activity 2需要取得Acitvity 1的資料時,透過getExtras()把資料放到Bundle(),最後用getString(key),把Acitvity 1傳遞的資料取出來。

不過在撰寫這部分的程式,不注意可能會發生底下的錯誤
java.lang.RuntimeException: Unable to start activity ComponentInfo{com.example.intentbundle/com.example.intentbundle.Result}: java.lang.NullPointerException

這個是由於資料是透過Bundle放到Intent裡面傳遞,在透過Bundle取出來。如果沒有放進去或者取出錯誤,才會導致Eclipse執行產生NullPointerException的例外錯誤。

以上為一個範例程式,輸入三個分數,然後數值會傳遞到計算平均的Activity 2。但執行Enter後發生以下錯誤,也就是NullPointerException。

整個錯誤訊息
E/AndroidRuntime(7342): FATAL EXCEPTION: main
E/AndroidRuntime(7342): java.lang.RuntimeException: Unable to start activity ComponentInfo{com.example.intentbundle/com.example.intentbundle.Result}: java.lang.NullPointerException
E/AndroidRuntime(7342): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2180)
E/AndroidRuntime(7342): at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2230)
E/AndroidRuntime(7342): at android.app.ActivityThread.access$600(ActivityThread.java:141)
E/AndroidRuntime(7342): at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1234)
E/AndroidRuntime(7342): at android.os.Handler.dispatchMessage(Handler.java:99)
E/AndroidRuntime(7342): at android.os.Looper.loop(Looper.java:137)
E/AndroidRuntime(7342): at android.app.ActivityThread.main(ActivityThread.java:5041)
E/AndroidRuntime(7342): at java.lang.reflect.Method.invokeNative(Native Method)
E/AndroidRuntime(7342): at java.lang.reflect.Method.invoke(Method.java:511)
E/AndroidRuntime(7342): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:793)
E/AndroidRuntime(7342): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:560)
E/AndroidRuntime(7342): at dalvik.system.NativeStart.main(Native Method)
E/AndroidRuntime(7342): Caused by: java.lang.NullPointerException
E/AndroidRuntime(7342): at com.example.intentbundle.Result.showResult(Result.java:51)
E/AndroidRuntime(7342): at com.example.intentbundle.Result.onCreate(Result.java:24)
E/AndroidRuntime(7342): at android.app.Activity.performCreate(Activity.java:5104)
E/AndroidRuntime(7342): at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1080)
E/AndroidRuntime(7342): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2144)
E/AndroidRuntime(7342): ... 11 more

可以看到編譯器指出錯誤是由於Result.java裡面的51行的showResult() method導致。
E/AndroidRuntime(7342):  at com.example.intentbundle.Result.showResult(Result.java:51)

在Activity 2的Result.java中,看起來並沒有太大的問題。

Bundle bundle = this.getIntent().getExtras();
double chinese = Double.parseDouble(bundle.getString("chinese"));
double english = Double.parseDouble(bundle.getString("english"));
double math = Double.parseDouble(bundle.getString("math"));

再去看Activity 1的MainActivity.java,

Intent intent = new Intent();
intent.setClass(MainActivity.this, Result.class);
Bundle bundle = new Bundle();
bundle.putString("chinese", etChinese.getText().toString());
bundle.putString("english", etEnglish.getText().toString());
bundle.putString("math", etMath.getText().toString());
intent.putExtras(intent);
startActivity(intent);
發現了在putExtras()的時候並不是把Bundle()放進去,應該要改為intent.putExtras(bundle),難怪會出現NullPointer的error。

更改成以下

Intent intent = new Intent();
intent.setClass(MainActivity.this, Result.class);
Bundle bundle = new Bundle();
bundle.putString("chinese", etChinese.getText().toString());
bundle.putString("english", etEnglish.getText().toString());
bundle.putString("math", etMath.getText().toString());
intent.putExtras(bundle);
startActivity(intent);

就可以順利看到程式執行的結果了
其實Eclipse的錯誤訊息可以幫助我們找到Android程式上撰寫的錯誤,多花點心思Google都會有答案。

沒有留言:

張貼留言