【问题标题】:Scrolling Listview in Android causing out of memory exception在Android中滚动Listview导致内存不足异常
【发布时间】:2013-11-21 11:44:13
【问题描述】:

我是 android 新手。我在 List Adaptor 中使用 HolderView() 方法做了一个 Listview,即使这样我也出现了内存不足异常。谁能告诉我哪里做错了。

代码

public class CustomView extends Activity {
    private static final String AUDIO_RECORDER_FOLDER = "AudioRecorder";
     ListView listview;
     private List<String> myList;
     private List<String> myDuration;
     private List<String> myListPath;

    @SuppressLint("SimpleDateFormat")
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
                myList = new ArrayList<String>();   
                myDuration = new ArrayList<String>();
                myListPath = new ArrayList<String>();
               //Fetching Deatil's from a folder from a SDCard
               String filepath = Environment.getExternalStorageDirectory().getPath();

        File file = new File(filepath, AUDIO_RECORDER_FOLDER);

        File list[] = file.listFiles();
        String filePath = file.getAbsolutePath(); 
        String fileName;
        String absolutePath;
        Date date;
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); // Set your date format;
        String currentFileName;
        for( int i=0; i< list.length; i++)
        {
            fileName = list[i].getName();
            absolutePath = filePath+"/"+fileName;
            myListPath.add(absolutePath);
            File f = new File(absolutePath);
            MediaPlayer mp = new MediaPlayer();
            FileInputStream fs;
            FileDescriptor fd;
            int duration = 0;
            try {
                fs = new FileInputStream(f);
                fd = fs.getFD();
                mp.setDataSource(fd);
                mp.prepare(); // might be optional

                duration= mp.getDuration();
                mp.release();
            } catch (FileNotFoundException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            } catch (IOException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }


            String file1[] =fileName.split(".mp3");
            long mydate = Long.parseLong(file1[0]);
            date = new Date(mydate)  ;
            currentFileName = sdf.format(date);
            currentFileName+=".mp3";
            myList.add(currentFileName);
            StringBuffer buf = new StringBuffer();
            int a = (int) TimeUnit.MILLISECONDS.toMinutes(duration);
            int b = (int) (TimeUnit.MILLISECONDS.toSeconds(duration) -  TimeUnit.MINUTES.toSeconds(a));
            buf.append(String.format("%02d", a));
            buf.append(":");
            buf.append(String.format("%02d", b));
            myDuration.add(buf.toString());
        }

        setContentView(R.layout.activity_list_view);
        listview = (ListView)findViewById(R.id.list);
        listview.setAdapter(new dataListAdapter(myList,myDuration,img));
        setButtonHandlers(); 

    }

    private void setButtonHandlers() {
        ((ImageView) findViewById(R.id.backBtn)).setOnClickListener(btnClick);
    }
    private View.OnClickListener btnClick = new View.OnClickListener() {
        @Override
        public void onClick(View v) {
        //sIntent i = getIntent();
        finishFromChild(getParent());
        }
        };
    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.activity_list_view, menu);
                return true;
    }
      class dataListAdapter extends BaseAdapter {
            List<String> Title, Detail;

            dataListAdapter() {
                Title = null;
                Detail = null;
            }

            public dataListAdapter(List<String> text,List<String> text1,int text3) {
                Title = text;
                Detail = text1;

            }

            public int getCount() {
                // TODO Auto-generated method stub
                return Title.size();
            }

            public Object getItem(int arg0) {
                // TODO Auto-generated method stub
                return null;
            }

            public long getItemId(int position) {
                // TODO Auto-generated method stub
                return position;
            }

            public View getView(final int position, View convertView, ViewGroup parent) {
                final Holder mHolder;
                LayoutInflater inflater;
                TextView title, detail;
                ImageView img;
                inflater = getLayoutInflater();
                mHolder = new Holder();
                mHolder.id = position;

                if(convertView == null) {
                    convertView = inflater.inflate(R.layout.list, parent, false);
                    title = (TextView) convertView.findViewById(R.id.name);
                    detail = (TextView) convertView.findViewById(R.id.duration);
                    mHolder.name = (TextView) convertView.findViewById(R.id.name);
                    mHolder.duration = (TextView) convertView.findViewById(R.id.duration);

                    //On Click Listener to play file when File Name is clicked
                    convertView.setOnClickListener(new View.OnClickListener() {
                        @Override
                        public void onClick(View v) {
                            // TODO Auto-generated method stub
                            String path = myListPath.get(position);
                            Intent intent = new Intent();  
                            intent.setAction(android.content.Intent.ACTION_VIEW);  
                            File file = new File(path);  
                            intent.setDataAndType(Uri.fromFile(file), "audio/*");  
                            startActivity(intent);

                        }
                    });
                    mHolder.name.setOnClickListener(new View.OnClickListener() {
                        @Override
                        public void onClick(View v) {
                            // TODO Auto-generated method stub
                            String path = myListPath.get(position);
                            Intent intent = new Intent();  
                            intent.setAction(android.content.Intent.ACTION_VIEW);  
                            File file = new File(path);  
                            intent.setDataAndType(Uri.fromFile(file), "audio/*");  
                            startActivity(intent);

                        }
                    });
                    //On Click Listener to play file when  Duration of the File is clicked
                    mHolder.duration.setOnClickListener(new View.OnClickListener() {
                        @Override
                        public void onClick(View v) {
                            // TODO Auto-generated method stub
                            String path = myListPath.get(position);
                            Intent intent = new Intent();  
                            intent.setAction(android.content.Intent.ACTION_VIEW);  
                            File file = new File(path);  
                            intent.setDataAndType(Uri.fromFile(file), "audio/*");  
                            startActivity(intent);

                        }
                    });
                    title.setText(Title.get(position).toString());
                    detail.setText(Detail.get(position).toString());

                    convertView.setTag(mHolder);
                }else{
                    convertView = inflater.inflate(R.layout.list, parent, false);
                    title = (TextView) convertView.findViewById(R.id.name);
                    detail = (TextView) convertView.findViewById(R.id.duration);
                    mHolder.name = (TextView) convertView.findViewById(R.id.name);
                    mHolder.duration = (TextView) convertView.findViewById(R.id.duration);

                    //On Click Listener to play file when File Name is clicked
                    convertView.setOnClickListener(new View.OnClickListener() {
                        @Override
                        public void onClick(View v) {
                            String path = myListPath.get(position);
                            Intent intent = new Intent();  
                            intent.setAction(android.content.Intent.ACTION_VIEW);  
                            File file = new File(path);  
                            intent.setDataAndType(Uri.fromFile(file), "audio/*");  
                            startActivity(intent);
                        }
                    });
                    mHolder.name.setOnClickListener(new View.OnClickListener() {
                        @Override
                        public void onClick(View v) {
                            String path = myListPath.get(position);
                            Intent intent = new Intent();  
                            intent.setAction(android.content.Intent.ACTION_VIEW);  
                            File file = new File(path);  
                            intent.setDataAndType(Uri.fromFile(file), "audio/*");  
                            startActivity(intent);
                        }
                    });
                    //On Click Listener to play file when  Duration of the File is clicked
                    mHolder.duration.setOnClickListener(new View.OnClickListener() {
                        @Override
                        public void onClick(View v) {
                            String path = myListPath.get(position);
                            Intent intent = new Intent();  
                            intent.setAction(android.content.Intent.ACTION_VIEW);  
                            File file = new File(path);  
                            intent.setDataAndType(Uri.fromFile(file), "audio/*");  
                            startActivity(intent);
                        }
                    });

                    title.setText(Title.get(position).toString());
                    detail.setText(Detail.get(position).toString());
                    convertView.setTag(mHolder);
                }
                return (convertView);
            }
        }
      class Holder {
            int id;
            TextView  name;
            TextView duration;
        }
}

【问题讨论】:

  • 您可以查看this

标签: java android listview android-listview


【解决方案1】:

这可能是因为您每次调用 getView() 时都会膨胀项目的布局。

if(convertView == null) {
    convertView = inflater.inflate(R.layout.list, parent, false);
    ...
}else{
    convertView = inflater.inflate(R.layout.list, parent, false);
    ...
}

您不应该在 else 语句中这样做,而应该使用给定的 convertView 并对其进行修改。

【讨论】:

    【解决方案2】:

    您在所有情况下都在夸大视图,您不应该这样做。 VieHolders 通常用于减少视图层次结构查找时间。

    看看这个答案Onclicklistner not working in fragment listview中的实现

    做这样的事情

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        View row = convertView;
        RecipesHolder holder = null;
        //recycling views
        if(null == row){
            row = inflater.inflate(layoutResourceId, parent, false);
            holder = new RecipesHolder();
            holder.imgIcon = (ImageView) row.findViewById(R.id.imageView1);
            holder.txtTitle = (TextView) row.findViewById(R.id.title);
            holder.category = (TextView) row.findViewById(R.id.category);
            holder.source = (TextView) row.findViewById(R.id.source);
            holder.country = (TextView) row.findViewById(R.id.country);
            holder.readytime = (TextView) row.findViewById(R.id.readytime);
            holder.tips = (Button) row.findViewById(R.id.tips);
            holder.fav = (Button) row.findViewById(R.id.fav);
            row.setTag(holder);
        }else{
            holder = (RecipesHolder)row.getTag();
        }
        Recipes ap = data[position];
    
        imageLoader.DisplayImage(ap.getIMAGENAME240(), holder.imgIcon);
        holder.txtTitle.setText(ap.getNAME());
        holder.category.setText(ap.getCATEGORY());
        holder.source.setText(ap.getSOURCE());
        holder.country.setText(ap.getCOUNTRY());
        holder.readytime.setText(ap.getREADYTIME());
    
        return row;
    }
    

    【讨论】:

      【解决方案3】:

      使用 RecyclerView 代替 ListView 和 Picasso 库来加载图像。

      【讨论】:

        猜你喜欢
        • 2012-12-15
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2017-05-13
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多