空对象引用上的'boolean java.util.ArrayList.isEmpty()'

时间:2018-08-26 18:14:52

标签: android android-recyclerview retrofit2 recycler-adapter

我正在尝试在同一个回收视图上进行2次不同的调用,其想法是从2次不同的请求中获取数据,并以足球比赛的ID显示经过验证的球队的盾牌。我知道错误的含义,但是,我真的不知道如何解决。 JSON文件有效,这是错误的。

E/AndroidRuntime: FATAL EXCEPTION: main
                  Process: com.example.cristhian.consumingapi, PID: 16520
                  java.lang.NullPointerException: Attempt to invoke virtual method 'boolean java.util.ArrayList.isEmpty()' on a null object reference
                      at com.example.cristhian.consumingapi.ListaPartidosAdapter.setupAdapter(ListaPartidosAdapter.java:99)
                      at com.example.cristhian.consumingapi.ListaPartidosAdapter.adicionarListaPartidos(ListaPartidosAdapter.java:89)
                      at com.example.cristhian.consumingapi.MainActivity$1.onResponse(MainActivity.java:76)
                      at retrofit2.ExecutorCallAdapterFactory$ExecutorCallbackCall$1$1.run(ExecutorCallAdapterFactory.java:68)
                      at android.os.Handler.handleCallback(Handler.java:751)
                      at android.os.Handler.dispatchMessage(Handler.java:95)
                      at android.os.Looper.loop(Looper.java:154)
                      at android.app.ActivityThread.main(ActivityThread.java:6119)
                      at java.lang.reflect.Method.invoke(Native Method)
                      at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:886)
                      at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:776)
Application terminated.

ListaPartidosAdapter

public class ListaPartidosAdapter extends RecyclerView.Adapter<ListaPartidosAdapter.ViewHolder> {

    private static final String TAG = "Football_Adapter";
    private ArrayList<Partido> dataset;
    private ArrayList<Stand> dataset_Stand;
    private Context context;

    public ListaPartidosAdapter(Context context) {
        this.context = context;
        dataset = new ArrayList<Partido>();
        dataset_Stand = new ArrayList<Stand>();
    }

    @Override
    public ListaPartidosAdapter.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
        View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.item_partidos, parent, false);
        return new ViewHolder(view);
    }   

    @Override
    public void onBindViewHolder(ListaPartidosAdapter.ViewHolder holder, int position) {
        Partido p = dataset.get(position);
        String status = p.getStatus();

        if (status.equals("SCHEDULED")){
            String status_ = "SCH";
            holder.status.setText(status_);
        }
        holder.utcDate.setText(p.getUtcDate());    
        Partido.EquipoCasa homeTeam = p.getHomeTeam();
        String id_homeTeam = homeTeam.getId();    
        holder.homeTeam.setText(homeTeam.getName());    
        Partido.EquipoVisita awayTeam = p.getAwayTeam();
        holder.awayTeam.setText(awayTeam.getName());    
        Stand s = dataset_Stand.get(position);
        Stand.Table table = (Stand.Table) s.getTable();
        Stand.Table.Equipo team = (Stand.Table.Equipo) table.getEquipo();
        String id_equipo = team.getId();
        holder.homeTeam.setText(team.getName());   

        if(id_homeTeam.equals(id_equipo)){
            Glide.with(context)
                .load(team.getCrestUrl())
                .centerCrop()
                .crossFade()
                .diskCacheStrategy(DiskCacheStrategy.ALL)
                .into(holder.team);
        }   
    }    
    @Override
    public int getItemCount() {
        return 0;
    }    
    public void adicionarListaPartidos(ArrayList<Partido> listaPartidos){
        setupAdapter(listaPartidos, null);
    }

    public void adicionarListaStands(ArrayList<Stand> listaStands){
        setupAdapter(null, listaStands);
    }

    private void setupAdapter(ArrayList<Partido> listaPartidos, ArrayList<Stand> listaStands) {
        if(!listaPartidos.isEmpty() && !listaStands.isEmpty()){
            addItemsToAdapter(listaPartidos,listaStands);
        }
    }

    public void addItemsToAdapter(ArrayList<Partido> listaPartidos, ArrayList<Stand> listaStands){
        notifyDataSetChanged();
    }

    public class ViewHolder extends RecyclerView.ViewHolder {    
        private TextView status;
        private TextView utcDate;
        private TextView homeTeam;
        private TextView awayTeam;
        public ImageView team;    

        public ViewHolder(View itemView) {
            super(itemView);

            status = (TextView) itemView.findViewById(R.id.status);
            utcDate = (TextView) itemView.findViewById(R.id.utcDate);
            homeTeam = (TextView) itemView.findViewById(R.id.homeTeam);
            awayTeam = (TextView) itemView.findViewById(R.id.awayTeam);
            team = (ImageView) itemView.findViewById(R.id.team);
        }
    }
}

这是我的MainActivity.java。

public class MainActivity extends AppCompatActivity {

    private Retrofit retrofit;
    private static final String TAG = "Football";
    private RecyclerView recyclerView;
    private ListaPartidosAdapter listaPartidosAdapter;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        recyclerView = (RecyclerView)findViewById(R.id.recyclerView);
        listaPartidosAdapter = new ListaPartidosAdapter(this);
        recyclerView.setAdapter(listaPartidosAdapter);
        recyclerView.setHasFixedSize(true);
        final LinearLayoutManager layoutManager = new LinearLayoutManager(this, VERTICAL, true);
        recyclerView.setLayoutManager(layoutManager);

        retrofit = new Retrofit.Builder()
                .baseUrl("http://api.football-data.org/v2/")
                .addConverterFactory(GsonConverterFactory.create())
                .build();

        obtenerDatos();
    }

    private void obtenerDatos() {

        Calendar calendar = Calendar.getInstance();
        SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd");
        String todayDate=df.format(calendar.getTime());
        calendar.add(Calendar.DATE,3);
        String endDate = df.format(calendar.getTime());

        Log.i(TAG, "todayDate : " + todayDate);
        Log.i(TAG, "endDate : " + endDate);

        footballdataService service = retrofit.create(footballdataService.class);
        Call<PartidosRespuesta> partidosRespuestaCall = service.obtenerlistaPartidos(todayDate,endDate);
        Call<StandingsRespuesta> standingsRespuestaCall = service.obtenerStandings();

        partidosRespuestaCall.enqueue(new Callback<PartidosRespuesta>() {
            @Override
            public void onResponse(Call<PartidosRespuesta> call, Response<PartidosRespuesta> response) {
                if(response.isSuccessful()) {
                    PartidosRespuesta partidosRespuesta = response.body();
                    List<Partido> listaPartidos = partidosRespuesta.getMatches();
                    listaPartidosAdapter.adicionarListaPartidos((ArrayList<Partido>) listaPartidos);

                }
                else {
                    Log.e(TAG, "onResponse: " + response.errorBody());
                }
            }

            @Override
            public void onFailure(Call<PartidosRespuesta> call, Throwable t) {
                Log.e(TAG, "onFailure: " + t.getMessage());
            }
        });

        standingsRespuestaCall.enqueue(new Callback<StandingsRespuesta>() {
            @Override
            public void onResponse(Call<StandingsRespuesta> call, Response<StandingsRespuesta> response) {
                if(response.isSuccessful()) {
                    StandingsRespuesta standingsRespuesta = response.body();
                    List<Stand> listaStands = standingsRespuesta.getStandings();
                    listaPartidosAdapter.adicionarListaStands((ArrayList<Stand>) listaStands);
                }
            }
            @Override
            public void onFailure(Call<StandingsRespuesta> call, Throwable t) {

            }
        });
    }

}

2 个答案:

答案 0 :(得分:1)

根据经验,将“无元素”表示为空列表是很糟糕的。从一开始就最好确保在这种情况下,您传递一个 empty 列表。就您而言,在此行之后

    List<Stand> listaStands = standingsRespuesta.getStandings();

插入以下内容

    if (listaStands == null) {
        listaStands = Collections.emptyList();
    }

(未经测试)

答案 1 :(得分:0)

您正在使用空值作为参数调用setupAdapter()函数,但尚未进行空检查。

private void setupAdapter(@Nullable ArrayList<Partido> listaPartidos, @Nullable ArrayList<Stand> listaStands) {
    if((listaPartidos != null && !listaPartidos.isEmpty()) //this might throw NPE
                     || (listaStands != null && !listaStands.isEmpty()) //This might throw NPE   ){
        addItemsToAdapter(listaPartidos,listaStands);
    }
}

您应根据您的应用逻辑添加空检查。