Android应用-尝试调用接口方法' int java.util.List.size()'在空对象引用上 [英] Android app - Attempt to invoke interface method 'int java.util.List.size()' on a null object reference

查看:56
本文介绍了Android应用-尝试调用接口方法' int java.util.List.size()'在空对象引用上的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在创建一个在gridview中显示电影海报的应用.我正在使用来自themoviedb.org的API.问题是我在运行应用程序时遇到了追随错误,并且正在努力解决该问题:

I'm creating an app that display movie poster in a gridview. I'm using an API from themoviedb.org. The problem is I'm getting the follow error when I run my app and I'm struggling to fix it:

07-18 20:27:39.244    2751-2751/? E/AndroidRuntime﹕ FATAL EXCEPTION: main
    Process: com.projmobileapp.pmdbadd.pmdb, PID: 2751
    java.lang.RuntimeException: Unable to start activity ComponentInfo{com.projmobileapp.pmdbadd.pmdb/com.projmobileapp.pmdbadd.pmdb.MainActivity}: android.view.InflateException: Binary XML file line #1: Error inflating class fragment
            at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2693)
            at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2758)
            at android.app.ActivityThread.access$900(ActivityThread.java:177)
            at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1448)
            at android.os.Handler.dispatchMessage(Handler.java:102)
            at android.os.Looper.loop(Looper.java:145)
            at android.app.ActivityThread.main(ActivityThread.java:5942)
            at java.lang.reflect.Method.invoke(Native Method)
            at java.lang.reflect.Method.invoke(Method.java:372)
            at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1400)
            at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1195)
     Caused by: android.view.InflateException: Binary XML file line #1: Error inflating class fragment
            at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:770)
            at android.view.LayoutInflater.inflate(LayoutInflater.java:483)
            at android.view.LayoutInflater.inflate(LayoutInflater.java:415)
            at android.view.LayoutInflater.inflate(LayoutInflater.java:366)
            at android.support.v7.app.AppCompatDelegateImplV7.setContentView(AppCompatDelegateImplV7.java:249)
            at android.support.v7.app.AppCompatActivity.setContentView(AppCompatActivity.java:106)
            at com.projmobileapp.pmdbadd.pmdb.MainActivity.onCreate(MainActivity.java:15)
            at android.app.Activity.performCreate(Activity.java:6289)
            at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1119)
            at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2646)
            at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2758)
            at android.app.ActivityThread.access$900(ActivityThread.java:177)
            at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1448)
            at android.os.Handler.dispatchMessage(Handler.java:102)
            at android.os.Looper.loop(Looper.java:145)
            at android.app.ActivityThread.main(ActivityThread.java:5942)
            at java.lang.reflect.Method.invoke(Native Method)
            at java.lang.reflect.Method.invoke(Method.java:372)
            at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1400)
            at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1195)
     Caused by: java.lang.NullPointerException: Attempt to invoke interface method 'int java.util.List.size()' on a null object reference
            at android.widget.ArrayAdapter.getCount(ArrayAdapter.java:330)
            at android.widget.GridView.setAdapter(GridView.java:201)
            at com.projmobileapp.pmdbadd.pmdb.MainActivityFragment.onCreateView(MainActivityFragment.java:53)
            at android.support.v4.app.Fragment.performCreateView(Fragment.java:1789)
            at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:924)
            at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1116)
            at android.support.v4.app.FragmentManagerImpl.addFragment(FragmentManager.java:1218)
            at android.support.v4.app.FragmentManagerImpl.onCreateView(FragmentManager.java:2170)
            at android.support.v4.app.FragmentActivity.onCreateView(FragmentActivity.java:300)
            at android.support.v7.app.AppCompatDelegateImplV7.callActivityOnCreateView(AppCompatDelegateImplV7.java:838)
            at android.support.v7.app.AppCompatDelegateImplV11.callActivityOnCreateView(AppCompatDelegateImplV11.java:34)
            at android.support.v7.app.AppCompatDelegateImplV7.onCreateView(AppCompatDelegateImplV7.java:826)
            at android.support.v4.view.LayoutInflaterCompatHC$FactoryWrapperHC.onCreateView(LayoutInflaterCompatHC.java:44)
            at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:732)
            at android.view.LayoutInflater.inflate(LayoutInflater.java:483)
            at android.view.LayoutInflater.inflate(LayoutInflater.java:415)
            at android.view.LayoutInflater.inflate(LayoutInflater.java:366)
            at android.support.v7.app.AppCompatDelegateImplV7.setContentView(AppCompatDelegateImplV7.java:249)
            at android.support.v7.app.AppCompatActivity.setContentView(AppCompatActivity.java:106)
            at com.projmobileapp.pmdbadd.pmdb.MainActivity.onCreate(MainActivity.java:15)
            at android.app.Activity.performCreate(Activity.java:6289)
            at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1119)
            at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2646)
            at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2758)
            at android.app.ActivityThread.access$900(ActivityThread.java:177)
            at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1448)
            at android.os.Handler.dispatchMessage(Handler.java:102)
            at android.os.Looper.loop(Looper.java:145)
            at android.app.ActivityThread.main(ActivityThread.java:5942)
            at java.lang.reflect.Method.invoke(Native Method)
            at java.lang.reflect.Method.invoke(Method.java:372)
            at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1400)
            at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1195)
07-18 20:27:39.244    2702-2702/? W/ResourcesManager﹕ Asset path '/system/framework/twframework.jar' does not exist or contains no resources.

这是我的代码

package com.projmobileapp.pmdbadd.pmdb;

import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.widget.GridView;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.ArrayList;
import java.util.List;

public class MainActivityFragment extends Fragment {

    private ArrayList<Movie> flavorList;


    public MainActivityFragment() {
    }

    MovieAdapter mMovieAdapter;


    public void onSaveInstanceState(Bundle outState) {
        outState.putParcelableArrayList("flavors", flavorList);
        super.onSaveInstanceState(outState);
    }


    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {

        View rootView = inflater.inflate(R.layout.fragment_main, container, false);

        mMovieAdapter = new MovieAdapter(getActivity(), flavorList);
        GridView listView = (GridView) rootView.findViewById(R.id.gridview_movie);
        listView.setAdapter(mMovieAdapter);
        updateMovie();

    return rootView;

    }


    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setHasOptionsMenu(true);
    }

    @Override
    public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
        // Inflate the menu; this adds items to the action bar if it is present.
        inflater.inflate(R.menu.mainactivityfragment, menu);
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        int id = item.getItemId();
        if (id == R.id.action_refresh) {
            updateMovie();
            return true;
        }
        return super.onOptionsItemSelected(item);
    }

    private void updateMovie() {
        FetchMovieTask movieTask = new FetchMovieTask();
        movieTask.execute();
    }

    class FetchMovieTask extends AsyncTask<Void, Void, List<Movie>> {
        private final String LOG_TAG = FetchMovieTask.class.getSimpleName();

        @Override
        protected List<Movie> doInBackground(Void... params) {
            HttpURLConnection urlConnection = null;
            BufferedReader reader = null;

            // Will contain the raw JSON response as a string.
            String movieJsonStr = null;

            try {
                URL url = new URL("http://api.themoviedb.org/3/discover/movie?sort_by=popularity.desc&api_key=InsertAPIKey");

                urlConnection = (HttpURLConnection) url.openConnection();
                urlConnection.setRequestMethod("GET");
                urlConnection.connect();

                // Read the input stream into a String
                InputStream inputStream = urlConnection.getInputStream();
                StringBuffer buffer = new StringBuffer();
                if (inputStream == null) {
                    // Nothing to do.
                    return null;
                }
                reader = new BufferedReader(new InputStreamReader(inputStream));

                String line;
                while ((line = reader.readLine()) != null) {

                    buffer.append(line + "\n");
                }

                if (buffer.length() == 0) {
                    // Stream was empty.  No point in parsing.
                    return null;
                }
                movieJsonStr = buffer.toString();

            } catch (IOException e) {
                Log.e(LOG_TAG, "Error ", e);
                return null;
            } finally {
                if (urlConnection != null) {
                    urlConnection.disconnect();
                }
                if (reader != null) {
                    try {
                        reader.close();
                    } catch (final IOException e) {
                        Log.e(LOG_TAG, "Error closing stream", e);
                    }
                }
            }
            try {
                return getMovieDataFromJson(movieJsonStr);
            } catch (JSONException j) {
                Log.e(LOG_TAG, "JSON Error", j);
            }
            return null;
        }

        private List<Movie> getMovieDataFromJson(String forecastJsonStr)
                throws JSONException {
            List<Movie> movies = new ArrayList<>();
            JSONObject movieJson = new JSONObject(forecastJsonStr);
            JSONArray movieArray = movieJson.getJSONArray("results");
            for (int i = 0; i < movieArray.length(); i++) {
                JSONObject movie = movieArray.getJSONObject(i);
                Movie movie1 = new Movie(movieJson.getString("original_title"), movieJson.getDouble("vote_average"), movieJson.getString("release_date"), movieJson.getString("overview"), movieJson.getString("poster_path"));
                movies.add(movie1);

            }
            return movies;
        }





        @Override
        protected void onPostExecute(List<Movie> movies) {
            if (movies != null) {
                mMovieAdapter.clear();
                for(Movie dayForecastStr : movies) {
                    mMovieAdapter.add(dayForecastStr);
                }
                // New data is back from the server.  Hooray!
            }
        }
    }


}

有人可以建议吗

推荐答案

我相信您应该将列表保存到 saveInstanceState 上的捆绑包中以进行轮换,实际上您并没有读回它如果bundle不为null,请在onCreate或onCreateView中使用.另外,我什至不确定电影是否真的是可打包的(请使用 http://parcelabler.com ),但即使这样,也无法使用,因为您需要使用 writeTypedList readTypedList 和NOT writeParcelableArrayList 读取后返回 List< Parcelable> ,而这不是您想要的).

I believe that you are supposedly saving the list out into the bundle on saveInstanceState for rotation, you're not actually reading it back in onCreate or onCreateView in case the bundle is not null. Also, I'm not even sure if Movie is actually a parcelable (use http://parcelabler.com ), but even if it were, this wouldn't work as you need to use writeTypedList and readTypedList and NOT writeParcelableArrayList (that returns List<Parcelable> on read, and that is NOT what you want).

但是当前的问题是您不应在此行中为适配器提供 null :

But the current problem is that you should not give a null to the adapter in this line:

mMovieAdapter = new MovieAdapter(getActivity(), flavorList);

初始化适配器并仅在实际有数据时进行设置,或使用空列表进行初始化.

Initialize the adapter and set it only when you actually have data, or initialize it with an empty list.

不过,实际上,请使用 writeTypedList readTypedList ,否则以后在保存状态时会遇到很多问题.

Really though, use writeTypedList and readTypedList, otherwise you'll run into a lot of issues later on with state saving.

这篇关于Android应用-尝试调用接口方法&amp;#39; int java.util.List.size()&amp;#39;在空对象引用上的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆