1

当我尝试从 oncreate() 函数调用 showQuestion() 方法时,会出现空指针异常,但如果我尝试通过按钮调用它,任何建议都可以。我想从 onCreate() 函数调用 showQuestion() 以便在活动打开时显示一条消息。

public class MainActivity extends Activity {
TextView txt;

Button bt;
int i=0;
static InputStream is = null;
static JSONObject jobj = null;
String line,results="";
static String json = "";
static JSONArray msgList = null;
@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    new asynt().execute();

    txt=(TextView) findViewById(R.id.textView1);
     bt= (Button) findViewById(R.id.button1);

    showQuestion(i);// null pointer exception
    bt.setOnClickListener(new OnClickListener() {

        @Override
        public void onClick(View v) {
            // TODO Auto-generated method stub
            i++;
            showQuestion(i);
        }
    });
}

 private void showQuestion(int i){
     try {
        JSONObject jsonobject = msgList.getJSONObject(i);
         String s = jsonobject.getString("messg");
        txt.setText(s);
    } catch (JSONException e) {
        e.printStackTrace();
    } 
 }

 public class asynt extends AsyncTask<Void, Void, JSONArray>{

    @Override
    protected JSONArray doInBackground(Void...vois) {
        JSONArray tha=null;;
        try{
            BufferedReader reader = new BufferedReader(new InputStreamReader(getAssets().open("questions.txt")));
            StringBuilder sb = new StringBuilder();

            while( (line = reader.readLine()) != null)
            {
                sb.append(line + "\n");
            }
            reader.close();
            json=sb.toString();
            }
            catch(Exception e){
            }

            try {
                jobj = new JSONObject(json);
                tha = jobj.getJSONArray("message");

            } catch (JSONException e) {

                e.printStackTrace();
            }
            return tha;

    }
     @Override
    protected void onPostExecute(JSONArray result) {
        // TODO Auto-generated method stub
        //super.onPostExecute(result);
        msgList = result;
    }
 }
}

更新:

09-11 21:14:39.751: E/AndroidRuntime(31440): FATAL EXCEPTION: main
09-11 21:14:39.751: E/AndroidRuntime(31440): java.lang.NullPointerException
09-11 21:14:39.751: E/AndroidRuntime(31440):    at      com.examp.ankurtesting.MainActivity.showQuestion(MainActivity.java:60)
09-11 21:14:39.751: E/AndroidRuntime(31440):    at com.examp.ankurtesting.MainActivity.access$0(MainActivity.java:58)
09-11 21:14:39.751: E/AndroidRuntime(31440):    at com.examp.ankurtesting.MainActivity$1.onClick(MainActivity.java:53)
09-11 21:14:39.751: E/AndroidRuntime(31440):    at android.view.View.performClick(View.java:4129)
09-11 21:14:39.751: E/AndroidRuntime(31440):    at android.view.View$PerformClick.run(View.java:17143)
09-11 21:14:39.751: E/AndroidRuntime(31440):    at android.os.Handler.handleCallback(Handler.java:615)
09-11 21:14:39.751: E/AndroidRuntime(31440):    at android.os.Handler.dispatchMessage(Handler.java:92)
09-11 21:14:39.751: E/AndroidRuntime(31440):    at android.os.Looper.loop(Looper.java:137)
09-11 21:14:39.751: E/AndroidRuntime(31440):    at android.app.ActivityThread.main(ActivityThread.java:4802)
09-11 21:14:39.751: E/AndroidRuntime(31440):    at java.lang.reflect.Method.invokeNative(Native Method)
09-11 21:14:39.751: E/AndroidRuntime(31440):    at java.lang.reflect.Method.invoke(Method.java:511)
09-11 21:14:39.751: E/AndroidRuntime(31440):    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:813)
09-11 21:14:39.751: E/AndroidRuntime(31440):    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:580)
09-11 21:14:39.751: E/AndroidRuntime(31440):    at dalvik.system.NativeStart.main(Native Method)
4

4 回答 4

0

可能是您 msgList尚未初始化,因此导致NPE

于 2013-09-11T15:59:58.463 回答
0

很确定变量 msgList 是抛出 NPE 的原因

    JSONObject jsonobject = msgList.getJSONObject(i);

您收到此错误的原因是因为 msgList 在 AsyncTask 完成之前为空。onCreate() 方法在 AsyncTask 完成之前执行并完成。当您看到并按下调用 showQuestion() 的按钮时,AsyncTask 已完成并设置 msgList 的值,这就是为什么按下按钮时不会出现错误的原因。不要在 onCreate 中调用此方法,而是在 onPostExecute 中调用它并将 onPreExecute 添加到您的 AsyncTask 以通知用户有后台工作。

public class asynt extends AsyncTask<Void, Void, JSONArray>{

   ProgressDialog dialog;

   @Override
   public void onPreExecute() {
        dialog = new ProgressDialog(context);
        dialog.show();
   }

   @Override
   protected JSONArray doInBackground(Void...vois) {
        ...
        return tha;
   }

   @Override
   protected void onPostExecute(JSONArray result) {
       if(dialog.isShowing()) {
           dialog.dismiss();
       }
       msgList = result;
       showQuestion(i);
   }
}

从 onCreate() 方法中删除 showQuestion(i)。AsyncTask 的 onPostExecute 方法在主 UI 线程中运行。

附带说明一下,养成给变量起更好名称的习惯。在 Eclipse 中按下 Ctrl+Space 会自动完成,因此您可以使用 LoadMessageListAsync 之类的名称而不是 asynt,它使代码维护变得更好

于 2013-09-11T16:33:19.983 回答
0

你的方法

private void showQuestion(int i){
     try {
        JSONObject jsonobject = quesList.getJSONObject(i);
         String s = jsonobject.getString("messg");
        txt.setText(s);
    } catch (JSONException e) {
        e.printStackTrace();
    } 

quesList它在哪里声明或初始化???

其他要点

可能是你quesList.getJSONObject(i);返回的NULL

所以这个jsonobject.getString("messg"); 将抛出NullPointerException

于 2013-09-11T15:21:47.983 回答
0

我在您的示例中找不到 quesList 。如果您的意思是 msgList,我在想,异步任务的结果尚未写入 msgList。您在任务开始后不久就调用了 showQuestion。你正在做的文件 io 有时很慢。也许,索引为 0 的 JSONObject 只是空值。你已经检查过这个了吗?

于 2013-09-11T15:14:43.520 回答