Search code examples
androidandroid-recyclerviewandroid-sqliteout-of-memory

Android: RecyclerView and SQLite Database OutOfMemeory error?


So I'm making a coffee roasting app. I'm using a database to save a roast profile, and then I'm listing it in another activity with a RecyclerView. The problem is, I'm either getting an OutOfMemery error, or logcat just keeps looping back in forth while at a black screen and doesn't shut down the app. Here's the code for the activity I'm having issues with:

RoastListActivity:

package com.coffeeroastingtimer.coffeeroastingtimer.Activities;

import androidx.annotation.RequiresApi;
import androidx.appcompat.app.AlertDialog;
import androidx.appcompat.app.AppCompatActivity;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;

import android.os.Build;
import android.os.Bundle;

import com.coffeeroastingtimer.coffeeroastingtimer.Data.DatabaseHandler;
import com.coffeeroastingtimer.coffeeroastingtimer.Model.RoastProfile;
import com.coffeeroastingtimer.coffeeroastingtimer.R;
import com.coffeeroastingtimer.coffeeroastingtimer.UI.RecyclerViewAdapter;

import java.util.ArrayList;
import java.util.List;

public class RoastListActivity extends AppCompatActivity
{
    private RecyclerView recyclerView;
    private RecyclerViewAdapter recyclerViewAdapter;
    private List<RoastProfile> roastProfileList;
    private List<RoastProfile> listItems;
    private DatabaseHandler db;
    private AlertDialog.Builder dialogBuilder;
    private AlertDialog dialog;

    @RequiresApi(api = Build.VERSION_CODES.O)
    @Override
    protected void onCreate(Bundle savedInstanceState)
    {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_roast_list);

        db = new DatabaseHandler(this);
        //db.getRoastProfileCount();
        recyclerView = (RecyclerView) findViewById(R.id.recyclerViewID);
        recyclerView.setHasFixedSize(true);
        recyclerView.setLayoutManager(new LinearLayoutManager(this));

        roastProfileList = new ArrayList<>();
        listItems = new ArrayList<>();

        roastProfileList = db.getAllRoastProfiles();

        for (RoastProfile profile : roastProfileList)
        {
            RoastProfile roastProfile = new RoastProfile();
            roastProfile.setName(profile.getName());
            roastProfile.setId(profile.getId());
            roastProfile.setFirstCrack(profile.getFirstCrack());
            roastProfile.setMaillard(profile.getMaillard());
            roastProfile.setYellow(profile.getYellow());
            roastProfile.setTemp(profile.getTemp());
            roastProfile.setEndTime(profile.getEndTime());
            roastProfile.setDateAdded(profile.getDateAdded());

            listItems.add(roastProfile);
        }

        recyclerViewAdapter = new RecyclerViewAdapter(this, listItems);
        recyclerView.setAdapter(recyclerViewAdapter);


    }
}

RecyclerViewAdapter:

package com.coffeeroastingtimer.coffeeroastingtimer.UI;

import android.app.AlertDialog;
import android.content.Context;
import android.content.Intent;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;

import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;

import com.coffeeroastingtimer.coffeeroastingtimer.Activities.RoastDetailsActivity;
import com.coffeeroastingtimer.coffeeroastingtimer.Data.DatabaseHandler;
import com.coffeeroastingtimer.coffeeroastingtimer.Model.RoastProfile;
import com.coffeeroastingtimer.coffeeroastingtimer.R;

import java.util.List;

public class RecyclerViewAdapter extends RecyclerView.Adapter<RecyclerViewAdapter.ViewHolder>
{
    private Context context;
    private List<RoastProfile> roastProfiles;
    private AlertDialog.Builder alertDialogBuilder;
    private AlertDialog dialog;
    private LayoutInflater inflater;

    public RecyclerViewAdapter(Context context, List<RoastProfile> roastProfiles)
    {
        this.context = context;
        this.roastProfiles = roastProfiles;
    }

    @NonNull
    @Override
    public RecyclerViewAdapter.ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType)
    {
        View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.roast_list_row, parent, false);

        return new ViewHolder(view, context);
    }

    @Override
    public void onBindViewHolder(@NonNull ViewHolder holder, int position)
    {
        RoastProfile roastProfile = roastProfiles.get(position);

        holder.row_beanName.setText(roastProfile.getName());
        holder.row_date.setText(roastProfile.getDateAdded());
    }

    @Override
    public int getItemCount()
    {
        return roastProfiles.size();
    }

    public class ViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener
    {
        public TextView row_beanName;
        public TextView row_date;
        public Button row_editButton;
        public Button row_deleteButton;
        public int row_id;

        public ViewHolder(@NonNull View view, Context ctx)
        {
            super(view);

            context = ctx;

            row_beanName = (TextView) view.findViewById(R.id.row_name);
            row_date = (TextView) view.findViewById(R.id.row_dateAdded);

            row_editButton = (Button) view.findViewById(R.id.editButton);
            row_deleteButton = (Button) view.findViewById(R.id.deleteButton);

            view.setOnClickListener(new View.OnClickListener()
            {
                @Override
                public void onClick(View v)
                {
                    int position = getAdapterPosition();

                    RoastProfile roastProfile = roastProfiles.get(position);

                    Intent intent = new Intent(context, RoastDetailsActivity.class);
                    intent.putExtra("name", roastProfile.getName());
                    intent.putExtra("date", roastProfile.getDateAdded());
                    intent.putExtra("id", roastProfile.getId());
                    intent.putExtra("temp", roastProfile.getTemp());
                    intent.putExtra("end", roastProfile.getEndTime());
                    intent.putExtra("fc", roastProfile.getFirstCrack());
                    intent.putExtra("maillard", roastProfile.getMaillard());
                    intent.putExtra("yellow", roastProfile.getYellow());

                    context.startActivity(intent);
                }
            });


        }

        @Override
        public void onClick(View v)
        {
            switch(v.getId())
            {
                case R.id.editButton:
                    int position = getAdapterPosition();
                    RoastProfile roastProfile = roastProfiles.get(position);

                    editItem(roastProfile);
                    break;
                case R.id.deleteButton:
                    position = getAdapterPosition();
                    roastProfile = roastProfiles.get(position);
                    deleteItem(roastProfile.getId());

                    break;
            }
        }

        public void deleteItem(final int id)
        {
            alertDialogBuilder = new AlertDialog.Builder(context);

            inflater = LayoutInflater.from(context);
            View view = inflater.inflate(R.layout.confirmation_dialog, null);

            Button noButton = view.findViewById(R.id.noButton);
            Button yesButton = view.findViewById(R.id.yesButton);

            alertDialogBuilder.setView(view);
            dialog = alertDialogBuilder.create();
            dialog.show();

            noButton.setOnClickListener(new View.OnClickListener()
            {
                @Override
                public void onClick(View v)
                {
                    dialog.dismiss();
                }
            });

            yesButton.setOnClickListener(new View.OnClickListener()
            {
                @Override
                public void onClick(View v)
                {
                    DatabaseHandler db = new DatabaseHandler(context);

                    db.deleteRoastProfile(id);
                    roastProfiles.remove(getAdapterPosition());
                    notifyItemRemoved(getAdapterPosition());

                    dialog.dismiss();
                }
            });
        }

        public void editItem(final RoastProfile roastProfile)
        {
            alertDialogBuilder = new AlertDialog.Builder(context);

            inflater = LayoutInflater.from(context);
            final View view = inflater.inflate(R.layout.popup, null);

            final EditText nameEdit = (EditText) view.findViewById(R.id.nameEditID);
            final EditText tempEdit = (EditText) view.findViewById(R.id.tempEditID);
            final EditText endEdit = (EditText) view.findViewById(R.id.endEditID);
            final EditText yellowEdit = (EditText) view.findViewById(R.id.yellowEditID);
            final EditText maillardEdit = (EditText) view.findViewById(R.id.maillardEditID);
            final EditText fcEdit = (EditText) view.findViewById(R.id.fcEditID);

            final TextView title = (TextView) view.findViewById(R.id.editTitleTextID);

            title.setText("Edit Roast Profile");

            Button saveButton = (Button) view.findViewById(R.id.saveEditsButtonID);

            alertDialogBuilder.setView(view);
            dialog = alertDialogBuilder.create();
            dialog.show();

            nameEdit.setText(roastProfile.getName());
            tempEdit.setText(roastProfile.getTemp());
            endEdit.setText(roastProfile.getEndTime());
            yellowEdit.setText(roastProfile.getYellow());
            maillardEdit.setText(roastProfile.getMaillard());
            fcEdit.setText(roastProfile.getFirstCrack());

            saveButton.setOnClickListener(new View.OnClickListener()
            {
                @Override
                public void onClick(View v)
                {
                    DatabaseHandler db = new DatabaseHandler(context);

                    roastProfile.setName(nameEdit.getText().toString());
                    roastProfile.setTemp(tempEdit.getText().toString());
                    roastProfile.setEndTime(endEdit.getText().toString());
                    roastProfile.setYellow(yellowEdit.getText().toString());
                    roastProfile.setMaillard(maillardEdit.getText().toString());
                    roastProfile.setFirstCrack(fcEdit.getText().toString());

                    db.updateRoastProfile(roastProfile);

                    dialog.dismiss();
                }
            });
        }
    }
}

Here's one of the places the issue could be in the DatabaseHandler class:

 public List<RoastProfile> getAllRoastProfiles()
    {
        SQLiteDatabase db = this.getReadableDatabase();

        List<RoastProfile> roastProfileList = new ArrayList<>();

        Cursor cursor = db.query(Constants.TABLE_NAME, new String[]
                        {
                        Constants.KEY_ID, Constants.KEY_BEAN_NAME, Constants.KEY_PREHEAT_TEMP,
                        Constants.KEY_YELLOW_PHASE, Constants.KEY_MAILLARD_PHASE, Constants.KEY_FIRST_CRACK,
                        Constants.KEY_END_TIME, Constants.KEY_DATE_ADDED
                        },
                null, null, null, null,
                Constants.KEY_DATE_ADDED + " DESC");

        if(cursor.moveToFirst())
        {
            do
            {
                RoastProfile roastProfile = new RoastProfile();
                roastProfile.setId(Integer.parseInt(cursor.getString(cursor.getColumnIndex(Constants.KEY_ID))));
                roastProfile.setName(cursor.getString(cursor.getColumnIndex(Constants.KEY_BEAN_NAME)));
                roastProfile.setTemp(cursor.getString(cursor.getColumnIndex(Constants.KEY_PREHEAT_TEMP)));
                roastProfile.setYellow(cursor.getString(cursor.getColumnIndex(Constants.KEY_YELLOW_PHASE)));
                roastProfile.setMaillard(cursor.getString(cursor.getColumnIndex(Constants.KEY_MAILLARD_PHASE)));
                roastProfile.setFirstCrack(cursor.getString(cursor.getColumnIndex(Constants.KEY_FIRST_CRACK)));
                roastProfile.setEndTime(cursor.getString(cursor.getColumnIndex(Constants.KEY_END_TIME)));

                LocalDateTime time = Instant.ofEpochMilli(cursor.getLong(cursor.getColumnIndex(Constants.KEY_DATE_ADDED))).atZone(ZoneId.systemDefault()).toLocalDateTime();
                DateTimeFormatter dtf = DateTimeFormatter.ofPattern("MM/dd/yyyy HH:mm:ss");

                String formattedDate = time.format(dtf);
                roastProfile.setDateAdded(formattedDate);

                roastProfileList.add(roastProfile);

            } while(cursor.moveToFirst());
        }

        return roastProfileList;
    }

It for whatever reason isn't showing the OutOfMemory error anymore, so I can't get the logcat for that, but here's the one for the infinite loop:

2020-06-04 11:03:01.834 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/TextToSpeech: Sucessfully bound to com.google.android.tts
2020-06-04 11:03:01.877 15957-15982/com.coffeeroastingtimer.coffeeroastingtimer D/EGL_emulation: eglMakeCurrent: 0xf068b1c0: ver 2 0 (tinfo 0xc49e7020)
2020-06-04 11:03:01.898 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/TextToSpeech: Connected to ComponentInfo{com.google.android.tts/com.google.android.tts.service.GoogleTTSService}
2020-06-04 11:03:01.899 15957-15982/com.coffeeroastingtimer.coffeeroastingtimer D/EGL_emulation: eglMakeCurrent: 0xf068b1c0: ver 2 0 (tinfo 0xc49e7020)
2020-06-04 11:03:01.902 15957-16013/com.coffeeroastingtimer.coffeeroastingtimer I/TextToSpeech: Set up connection to ComponentInfo{com.google.android.tts/com.google.android.tts.service.GoogleTTSService}
2020-06-04 11:03:02.319 15957-15982/com.coffeeroastingtimer.coffeeroastingtimer D/EGL_emulation: eglMakeCurrent: 0xf068b1c0: ver 2 0 (tinfo 0xc49e7020)
2020-06-04 11:03:03.019 15957-15982/com.coffeeroastingtimer.coffeeroastingtimer D/EGL_emulation: eglMakeCurrent: 0xf068b1c0: ver 2 0 (tinfo 0xc49e7020)
2020-06-04 11:03:03.044 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer D/Saved: Saved  to DB
2020-06-04 11:03:03.062 15957-15982/com.coffeeroastingtimer.coffeeroastingtimer D/EGL_emulation: eglMakeCurrent: 0xf068b1c0: ver 2 0 (tinfo 0xc49e7020)
2020-06-04 11:03:03.077 15957-15982/com.coffeeroastingtimer.coffeeroastingtimer D/EGL_emulation: eglMakeCurrent: 0xf068b1c0: ver 2 0 (tinfo 0xc49e7020)
2020-06-04 11:03:05.335 15957-15982/com.coffeeroastingtimer.coffeeroastingtimer D/EGL_emulation: eglMakeCurrent: 0xf068b1c0: ver 2 0 (tinfo 0xc49e7020)
2020-06-04 11:03:06.294 15957-15975/com.coffeeroastingtimer.coffeeroastingtimer W/System: A resource failed to call close. 
2020-06-04 11:03:06.294 15957-15975/com.coffeeroastingtimer.coffeeroastingtimer W/System: A resource failed to call close. 
2020-06-04 11:03:06.295 15957-15975/com.coffeeroastingtimer.coffeeroastingtimer W/MediaPlayer-JNI: MediaPlayer finalized without being released
2020-06-04 11:03:07.758 15957-15973/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Background concurrent copying GC freed 838729(21MB) AllocSpace objects, 0(0B) LOS objects, 44% free, 30MB/54MB, paused 158us total 138.929ms
2020-06-04 11:03:09.840 15957-15973/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Background concurrent copying GC freed 1200544(31MB) AllocSpace objects, 0(0B) LOS objects, 27% free, 63MB/87MB, paused 155us total 248.451ms
2020-06-04 11:03:12.125 15957-15973/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Background concurrent copying GC freed 1685911(45MB) AllocSpace objects, 0(0B) LOS objects, 18% free, 104MB/128MB, paused 158us total 393.266ms
2020-06-04 11:03:14.761 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Waiting for a blocking GC Alloc
2020-06-04 11:03:14.976 15957-15973/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Background concurrent copying GC freed 2709517(64MB) AllocSpace objects, 0(0B) LOS objects, 16% free, 123MB/147MB, paused 240us total 614.552ms
2020-06-04 11:03:14.976 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: WaitForGcToComplete blocked Alloc on HeapTrim for 214.959ms
2020-06-04 11:03:14.976 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:17.523 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Waiting for a blocking GC Alloc
2020-06-04 11:03:18.015 15957-15973/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Background concurrent copying GC freed 2186455(57MB) AllocSpace objects, 0(0B) LOS objects, 15% free, 131MB/155MB, paused 158us total 729.423ms
2020-06-04 11:03:18.016 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: WaitForGcToComplete blocked Alloc on HeapTrim for 492.071ms
2020-06-04 11:03:24.223 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.254 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Alloc young concurrent copying GC freed 403799(9905KB) AllocSpace objects, 0(0B) LOS objects, 6% free, 180MB/192MB, paused 152us total 30.664ms
2020-06-04 11:03:24.300 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.300 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.331 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Alloc young concurrent copying GC freed 374227(9180KB) AllocSpace objects, 0(0B) LOS objects, 5% free, 180MB/192MB, paused 153us total 31.015ms
2020-06-04 11:03:24.373 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.373 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.403 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Alloc young concurrent copying GC freed 344690(8457KB) AllocSpace objects, 0(0B) LOS objects, 5% free, 181MB/192MB, paused 241us total 29.994ms
2020-06-04 11:03:24.442 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.442 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.472 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Alloc young concurrent copying GC freed 315154(7734KB) AllocSpace objects, 0(0B) LOS objects, 5% free, 181MB/192MB, paused 152us total 29.539ms
2020-06-04 11:03:24.510 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.510 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.540 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Alloc young concurrent copying GC freed 295447(7251KB) AllocSpace objects, 0(0B) LOS objects, 5% free, 182MB/192MB, paused 152us total 30.397ms
2020-06-04 11:03:24.574 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.574 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.604 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Alloc young concurrent copying GC freed 275739(6768KB) AllocSpace objects, 0(0B) LOS objects, 4% free, 182MB/192MB, paused 153us total 29.735ms
2020-06-04 11:03:24.636 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.636 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.665 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Alloc young concurrent copying GC freed 256040(6286KB) AllocSpace objects, 0(0B) LOS objects, 4% free, 183MB/192MB, paused 152us total 29.488ms
2020-06-04 11:03:24.695 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.695 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.725 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Alloc young concurrent copying GC freed 236359(5804KB) AllocSpace objects, 0(0B) LOS objects, 4% free, 183MB/192MB, paused 157us total 29.617ms
2020-06-04 11:03:24.758 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.758 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.788 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Alloc young concurrent copying GC freed 216666(5322KB) AllocSpace objects, 0(0B) LOS objects, 4% free, 183MB/192MB, paused 152us total 29.894ms
2020-06-04 11:03:24.813 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.813 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.843 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Alloc young concurrent copying GC freed 196959(4839KB) AllocSpace objects, 0(0B) LOS objects, 4% free, 183MB/192MB, paused 153us total 29.549ms
2020-06-04 11:03:24.865 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:24.865 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:25.850 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Clamp target GC heap from 208MB to 192MB
2020-06-04 11:03:25.850 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Alloc concurrent copying GC freed 177511(4363KB) AllocSpace objects, 0(0B) LOS objects, 4% free, 184MB/192MB, paused 168us total 984.860ms
2020-06-04 11:03:25.882 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc
2020-06-04 11:03:25.882 15957-15957/com.coffeeroastingtimer.coffeeroastingtimer I/eeroastingtime: Starting a blocking GC Alloc

Sorry if that's overkill on posting all those different code blocks, I just figured the more information the better.

Any help would be greatly appreciated!


Solution

  • In the do while loop in getAllRoastProfiles function, change the exit condition from

    cursor.moveToFirst()
    

    to

    cursor.moveToNext()
    

    Reason: cursor.moveToFirst() in the do while loop condition keeps the cursor at the first line, causing infinite loop and hence OutOfMemory exception is raised.