有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

java自定义Listview性能不佳,Listview项名称从数据库转换

我的问题是Listview的加载速度太慢,所以我的阵列适配器有点不稳定。我不知道如何改进它,或者在其中实现异步任务

public class RezeptArrayAdapter extends ArrayAdapter<String> {

public final Context context;
public final String[] values;




public RezeptArrayAdapter(Context context, String[] values) {
    super(context, R.layout.list_rezepte, values);
    this.context = context;
    this.values = values;
    //this.notifyDataSetChanged();

}




@Override
public View getView(int position, View convertView, ViewGroup parent) {
    LayoutInflater inflater = (LayoutInflater) context
        .getSystemService(Context.LAYOUT_INFLATER_SERVICE);



    // DatenBank Abfrage Angepasst auf den Array "context" View
    final DBHandler_Rezepte db_Rzpt = new DBHandler_Rezepte(context);

    //Einzelabfrage der Datenbank Ratings damit Sie weiter unten verarbeitet werden können
    ConDB_Rezepte Data1 = db_Rzpt.getConDB_Rezepte(1);
    ConDB_Rezepte Data2 = db_Rzpt.getConDB_Rezepte(2);
    ConDB_Rezepte Data3 = db_Rzpt.getConDB_Rezepte(3);
    ConDB_Rezepte Data4 = db_Rzpt.getConDB_Rezepte(4);
    ConDB_Rezepte Data5 = db_Rzpt.getConDB_Rezepte(5);
    ConDB_Rezepte Data6 = db_Rzpt.getConDB_Rezepte(6);
    ConDB_Rezepte Data7 = db_Rzpt.getConDB_Rezepte(7);
    ConDB_Rezepte Data8 = db_Rzpt.getConDB_Rezepte(8);
    ConDB_Rezepte Data9 = db_Rzpt.getConDB_Rezepte(9);
    ConDB_Rezepte Data10 = db_Rzpt.getConDB_Rezepte(10);
    ConDB_Rezepte Data11 = db_Rzpt.getConDB_Rezepte(11);
    ConDB_Rezepte Data12 = db_Rzpt.getConDB_Rezepte(12);
    ConDB_Rezepte Data13 = db_Rzpt.getConDB_Rezepte(13);
    ConDB_Rezepte Data14 = db_Rzpt.getConDB_Rezepte(14);
    ConDB_Rezepte Data15 = db_Rzpt.getConDB_Rezepte(15);
    ConDB_Rezepte Data16 = db_Rzpt.getConDB_Rezepte(16);
    ConDB_Rezepte Data17 = db_Rzpt.getConDB_Rezepte(17);
    ConDB_Rezepte Data18 = db_Rzpt.getConDB_Rezepte(18);
    ConDB_Rezepte Data19 = db_Rzpt.getConDB_Rezepte(19);
    ConDB_Rezepte Data20 = db_Rzpt.getConDB_Rezepte(20);
    ConDB_Rezepte Data21 = db_Rzpt.getConDB_Rezepte(21);
    ConDB_Rezepte Data22 = db_Rzpt.getConDB_Rezepte(22);
    ConDB_Rezepte Data23 = db_Rzpt.getConDB_Rezepte(23);
    ConDB_Rezepte Data24 = db_Rzpt.getConDB_Rezepte(24);
    ConDB_Rezepte Data25 = db_Rzpt.getConDB_Rezepte(25);
    ConDB_Rezepte Data26 = db_Rzpt.getConDB_Rezepte(26);
    ConDB_Rezepte Data27 = db_Rzpt.getConDB_Rezepte(27);
    ConDB_Rezepte Data28 = db_Rzpt.getConDB_Rezepte(28);
    ConDB_Rezepte Data29 = db_Rzpt.getConDB_Rezepte(29);
    ConDB_Rezepte Data30 = db_Rzpt.getConDB_Rezepte(30);



    View rowView = inflater.inflate(R.layout.list_rezepte, parent, false);
    TextView textView = (TextView) rowView.findViewById(R.id.label);
    ImageView imageView = (ImageView) rowView.findViewById(R.id.logo);
    RatingBar ratingbar1 = (RatingBar) rowView.findViewById(R.id.ratingBar1);

    //stellt ein das man die Ratingbar nicht clicken kann, somit bleibt die Steuerung erhalten. Sonst ist die Liste nicht mehr clickbar
    ratingbar1.setIsIndicator(true);



    textView.setText(values[position]);
    //TYPEFACE///////////
    Typeface tf = Typeface.createFromAsset(context.getAssets(),"fonts/OFLGoudyStMTT.ttf");
    textView.setTypeface(tf);



    // Change icon based on name
    String pos = values[position];

    int KuchenIcon = R.drawable.ic_kuchen;
    int MuffinIcon = R.drawable.ic_muffin;
    int PlaetzchenIcon = R.drawable.ic_plaetzchen;
    int ApfelkandiertIcon = R.drawable.ic_apfelkandiert;
    int OthersIcon = R.drawable.ic_others;



    //bei dem Equals Vergleich musste ich die GetRessource Methode nach dem Context senden, da die Array Class Context heißt.

    //System.out.println(s); //DEBUG Ausgabe


    if (pos.matches(Data1.getName()))  {
        imageView.setImageResource(KuchenIcon);
        ratingbar1.setRating(Data1.getrating());
        //context.getResources().getString(R.string.Rezept_01))
        //ratingbar1.setRating(Float.parseFloat(Data1.getrating()));

    } else if (pos.matches(Data2.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data2.getrating());

    } else if (pos.matches(Data3.getName())) {
        imageView.setImageResource(ApfelkandiertIcon);
        ratingbar1.setRating(Data3.getrating());

    } else if (pos.matches(Data4.getName())) {
        imageView.setImageResource(MuffinIcon);
        ratingbar1.setRating(Data4.getrating());

    } else if (pos.matches(Data5.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data5.getrating());

    } else if (pos.matches(Data6.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data6.getrating());

    } else if (pos.matches(Data7.getName())) {
        imageView.setImageResource(OthersIcon);
        ratingbar1.setRating(Data7.getrating());

    } else if (pos.matches(Data8.getName())) {
        imageView.setImageResource(KuchenIcon);
        ratingbar1.setRating(Data8.getrating());

    } else if (pos.matches(Data9.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data9.getrating());

    } else if (pos.matches(Data10.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data10.getrating());

    } else if (pos.matches(Data11.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data11.getrating());

    } else if (pos.matches(Data12.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data12.getrating());

    } else if (pos.matches(Data13.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data13.getrating());

    } else if (pos.matches(Data14.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data14.getrating());

    } else if (pos.matches(Data15.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data15.getrating());

    } else if (pos.matches(Data16.getName())) {
        imageView.setImageResource(KuchenIcon);
        ratingbar1.setRating(Data16.getrating());

    } else if (pos.matches(Data17.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data17.getrating());

    } else if (pos.matches(Data18.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data18.getrating());

    } else if (pos.matches(Data19.getName())) {
        imageView.setImageResource(ApfelkandiertIcon);
        ratingbar1.setRating(Data19.getrating());

    } else if (pos.matches(Data20.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data20.getrating());

    } else if (pos.matches(Data21.getName())) {
        imageView.setImageResource(MuffinIcon);
        ratingbar1.setRating(Data21.getrating());

    } else if (pos.matches(Data22.getName())) {
        imageView.setImageResource(KuchenIcon);
        ratingbar1.setRating(Data22.getrating());

    } else if (pos.matches(Data23.getName())) {
        imageView.setImageResource(KuchenIcon);
        ratingbar1.setRating(Data23.getrating());

    } else if (pos.matches(Data24.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data24.getrating());

    } else if (pos.matches(Data25.getName())) {
        imageView.setImageResource(KuchenIcon);
        ratingbar1.setRating(Data25.getrating());

    } else if (pos.matches(Data26.getName())) {
        imageView.setImageResource(KuchenIcon);
        ratingbar1.setRating(Data26.getrating());

    } else if (pos.matches(Data27.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data27.getrating());

    } else if (pos.matches(Data28.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data28.getrating());

    } else if (pos.matches(Data29.getName())) {
        imageView.setImageResource(PlaetzchenIcon);
        ratingbar1.setRating(Data29.getrating());

    } else if (pos.matches(Data30.getName())) {
        imageView.setImageResource(KuchenIcon);
        ratingbar1.setRating(Data30.getrating());


    }
    else {
        imageView.setImageResource(OthersIcon);
    }

    return rowView;
}








} 

共 (2) 个答案

  1. # 1 楼答案

    你做了很多不必要的事情。我简化了代码并添加了一些注释。简言之:

    1. 使用position查找应该提取哪些数据(它也可以是一个预取列表,将从数据库提取减少为一个查询)
    2. 您应该使用ViewHolder模式来回收和重用视图->;相当多的性能改进
    3. 您需要在getView()方法之外执行“静态”操作,因为加载字体之类的操作相当慢

    希望下面的代码能帮助你

    public class RezeptArrayAdapter extends ArrayAdapter<String> {
    
        public final Context context;
        public final String[] values;
        final DBHandler_Rezepte db_Rzpt;
        //TYPEFACE///////////
        Typeface tf;
    
    
        public RezeptArrayAdapter(Context context, String[] values) {
            super(context, R.layout.list_rezepte, values);
            this.context = context;
            this.values = values;
    
            // Do "static/reusable" stuff here
            // DatenBank Abfrage Angepasst auf den Array "context" View
            db_Rzpt = new DBHandler_Rezepte(context);
            //TYPEFACE///////////
            tf = Typeface.createFromAsset(context.getAssets(), "fonts/OFLGoudyStMTT.ttf");
        }
    
        // will be called quite often! Make it fast as possible!
        @Override
        public View getView(int position, View convertView, ViewGroup parent) {
            LayoutInflater inflater = (LayoutInflater) context
                    .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    
            //Einzelabfrage der Datenbank Ratings damit Sie weiter unten verarbeitet werden können
            ConDB_Rezepte data = db_Rzpt.getConDB_Rezepte(position);
    
            // To not do too much at once this tip for later: Use the ViewHolder pattern
            View rowView = inflater.inflate(R.layout.list_rezepte, parent, false);
            TextView textView = (TextView) rowView.findViewById(R.id.label);
            ImageView imageView = (ImageView) rowView.findViewById(R.id.logo);
            RatingBar ratingbar1 = (RatingBar) rowView.findViewById(R.id.ratingBar1);
    
            //stellt ein das man die Ratingbar nicht clicken kann, somit bleibt die Steuerung erhalten. Sonst ist die Liste nicht mehr clickbar
            ratingbar1.setIsIndicator(true);
    
            textView.setText(values[position]);
    
            textView.setTypeface(tf);
    
    
            // Change icon based on name
            String pos = values[position];
    
            // data should contain the information which icon should be shown!
            //int KuchenIcon = R.drawable.ic_kuchen;
            //int MuffinIcon = R.drawable.ic_muffin;
            //int PlaetzchenIcon = R.drawable.ic_plaetzchen;
            //int ApfelkandiertIcon = R.drawable.ic_apfelkandiert;
            //int OthersIcon = R.drawable.ic_others;
    
            // apply values/data to the view
            imageView.setImageResource(data.getIcon());
            ratingbar1.setRating(data.getrating());
    
            return rowView;
        }
    
    }
    

    更新:

    对于图标的问题,解决方案可能非常简单:您可以按名称获取图标。您所需要做的就是将图标的名称存储在数据库中

    完成此操作后,您可以使用以下方法加载可绘图项:

    public int getDrawableResource(String drawableName){
        return getResources().getIdentifier(drawableName, "drawable", getActivity().getPackageName());
    }
    

    因此,您只需将图标名称存储在数据库中,以便保存数据。getIcon()返回使用上述方法获得的资源id

  2. # 2 楼答案

    viewholder保存视图信息以避免重新创建

    static class ViewHolder { 
      member variables...
      TextView text;
    }
    

    然后,在检查convertView是否为null时,创建viewholder

    ViewHolder holder;
    
    if(convertView == null) {
            LayoutInflater inflater = (LayoutInflater) mContext
                    .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
            convertView = inflater.inflate(R.layout.layout, parent, false);
            // create the viewholder for the view
            holder = new ViewHolder();
            holder.text = (TextView) convertView.findViewById(R.id.textview);
            convertView.setTag(holder);
    } else {
        // Reuse the viewholder
        holder = (ViewHolder) convertView.getTag();
    }
    
    holder.text.setText("string");
    

    使用这种模式会更快,因为findviewbyd调用可能会很昂贵。这样你只做一次

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
    
        ViewHolder holder;
    
        if(convertView == null) {
            LayoutInflater inflater = (LayoutInflater) mContext
                .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
            convertView = inflater.inflate(R.layout.list_rezepte, parent, false);
            // create the viewholder for the view
            holder = new ViewHolder();
            holder.textView = (TextView) convertView.findViewById(R.id.label);
            holder.imageView = (ImageView) convertView.findViewById(R.id.logo);
            holder.ratingbar1 = (RatingBar) convertView.findViewById(R.id.ratingBar1);
            convertView.setTag(holder);
        } else {
            // Reuse the viewholder
            holder = (ViewHolder) convertView.getTag();
        }
    
        //Einzelabfrage der Datenbank Ratings damit Sie weiter unten verarbeitet werden können
        ConDB_Rezepte data = db_Rzpt.getConDB_Rezepte(position);
    
        //stellt ein das man die Ratingbar nicht clicken kann, somit bleibt die Steuerung erhalten. Sonst ist die Liste nicht mehr clickbar
        holder.ratingbar1.setIsIndicator(true);
    
        holder.textView.setText(values[position]);
    
        holder.textView.setTypeface(tf);
    
    
        // Change icon based on name
        String pos = values[position];
    
        // data should contain the information which icon should be shown!
        //int KuchenIcon = R.drawable.ic_kuchen;
        //int MuffinIcon = R.drawable.ic_muffin;
        //int PlaetzchenIcon = R.drawable.ic_plaetzchen;
        //int ApfelkandiertIcon = R.drawable.ic_apfelkandiert;
        //int OthersIcon = R.drawable.ic_others;
    
        // apply values/data to the view
        holder.imageView.setImageResource(data.getIcon());
        holder.ratingbar1.setRating(data.getrating());
    
        return convertView;
    }
    
    static class ViewHolder { 
    
        TextView textView;
        ImageView imageView;
        RatingBar ratingbar1;
    }
    

    }