2015-04-24 50 views
0

我試圖從SQLite數據庫獲取數據庫並試圖填充ListView並在ArrayList<String>中添加數據。 ListView很好地填充,但問題是ArrayList<String>沒有很好地填充。ArrayList <String>在CursorAdapter中無法正常工作

假設我有像在數據庫中的數據: 甲 乙 Ç d Ë ˚F ģ ħ 我 Ĵ ķ 大號 中號 Ñ ........ 我的ListView以這種方式顯示數據。但ArrayList<String>添加數據是這樣的: 甲 乙 Ç d Ë ˚F 甲 乙 Ç d Ë ˚F ģ ħ ......

這意味着我的ArrayList<String>取第6個值然後重複它,然後取下一個6的值然後再重複它.....。這意味着當我從列表視圖中單擊項目「H」時,ArrayList<String>顯示我「B」。我不知道它爲什麼會發生?

我的代碼,CustomList延伸AllCityListFragmentCursorAdapter

import java.util.ArrayList; 

import android.content.Context; 
import android.database.Cursor; 
import android.view.LayoutInflater; 
import android.view.View; 
import android.view.ViewGroup; 
import android.widget.CheckBox; 
import android.widget.CursorAdapter; 
import android.widget.TextView; 

public class CustomList extends CursorAdapter { 

    CheckBox favoriteBox; 
    TextView cityName, countryName; 
    ArrayList<String> city_name; 
    ArrayList<String> country_name; 
    ArrayList<String> country_short; 
    ArrayList<CheckBox> check_box; 

    public CustomList(Context context, Cursor c, ArrayList<String> city_name, 
      ArrayList<String> country_name, ArrayList<String> country_short, 
      ArrayList<CheckBox> check_box) { 
     super(context, c, 0); 
     this.city_name = city_name; 
     this.country_name = country_name; 
     this.country_short = country_short; 
     this.check_box = check_box; 
    } 

    @Override 
    public View newView(Context context, Cursor cursor, ViewGroup parent) { 

     LayoutInflater inflater = LayoutInflater.from(parent.getContext()); 
     View retView = inflater.inflate(R.layout.all_city_list, parent, false); 

     return retView; 
    } 

    @Override 
    public void bindView(final View view, Context context, Cursor cursor) { 
     cityName = (TextView) view.findViewById(R.id.cityName); 
     String cityS = cursor.getString(cursor.getColumnIndex("city_name")); 
     cityName.setText(cityS); 
     city_name.add(cityS);//adding value to ArrayList<String> 

     countryName = (TextView) view.findViewById(R.id.countryName); 
     String conS = cursor.getString(cursor.getColumnIndex("country_name")); 
     countryName.setText(conS); 
     country_name.add(conS);//adding value to ArrayList<String> 
     country_short.add("" 
       + cursor.getString(cursor.getColumnIndex("country_short")));//adding value to ArrayList<String> 

     favoriteBox = (CheckBox) view.findViewById(R.id.favoriteCheckBox); 
     check_box.add(favoriteBox); 
     if (cursor.getInt(cursor.getColumnIndex("favorite")) == 0) { 
      favoriteBox.setChecked(false); 
     } else { 
      favoriteBox.setChecked(true); 
     } 
    } 
} 

類延伸Fragment

import java.io.IOException; 
import java.util.ArrayList; 

import android.os.Bundle; 
import android.os.Handler; 
import android.support.v4.app.Fragment; 
import android.view.LayoutInflater; 
import android.view.View; 
import android.view.ViewGroup; 
import android.widget.AdapterView; 
import android.widget.AdapterView.OnItemLongClickListener; 
import android.widget.CheckBox; 
import android.widget.ListView; 
import android.widget.Toast; 

public class AllCityListFragment extends Fragment { 
    private CustomList customAdapter; 
    private DatabaseHelper databaseHelper; 
    ArrayList<String> city_name = new ArrayList<String>(); 
    ArrayList<String> country_name = new ArrayList<String>(); 
    ArrayList<String> country_short = new ArrayList<String>(); 
    ArrayList<CheckBox> check_box = new ArrayList<CheckBox>(); 

    public static final String ARG_OS = "OS"; 
    int pos; 
    String sql = ""; 

    ListView list; 
    View view; 

    @Override 
    public View onCreateView(LayoutInflater inflater, ViewGroup container, 
      Bundle savedInstanceState) { 
     view = inflater.inflate(R.layout.all_city_layout, null); 

     databaseHelper = new DatabaseHelper(view.getContext()); 

     try { 
      databaseHelper.createDataBase(); 
      databaseHelper.openDataBase(); 
     } catch (IOException e) { 
      // TODO Auto-generated catch block 
      Toast.makeText(view.getContext(), "Error: " + e.getMessage(), 
        Toast.LENGTH_LONG).show(); 
      e.printStackTrace(); 
     } 

     list = (ListView) view.findViewById(R.id.citylist); 
     list.setFocusable(false); 

     list.setOnItemClickListener(new AdapterView.OnItemClickListener() { 

      @Override 
      public void onItemClick(AdapterView<?> parent, View myview, 
        int position, long id) { 
       Toast.makeText(getActivity(), 
         position + " " + city_name.get(position), 
         Toast.LENGTH_LONG).show(); 
      } 
     }); 

      sql = "SELECT _id, city_name, country_name, country_short, favorite FROM city order by country_name asc;"; 


     new Handler().post(new Runnable() { 
      @Override 
      public void run() { 
       customAdapter = new CustomList(getActivity(), databaseHelper 
         .getResult(sql), city_name, country_name, 
         country_short, check_box); 

       list.setAdapter(customAdapter); 
      } 
     }); 

     return view; 
    } 

    @Override 
    public void onActivityCreated(Bundle savedInstanceState) { 
     super.onActivityCreated(savedInstanceState); 
    } 


} 

enter image description here

在這張圖片中,我點擊 「Shirajganj」,但Toast顯示我「230 Thakurgaon「position = 230是正確的,但city_name.get(230)應該是b e「Shirajganj」。我想這是做錯了,當我試圖增加價值ArrayList<String> binList在CustomList中。我怎麼解決這個問題?

+1

爲什麼不使用'Set'而不是'ArrayList'來避免重複值? –

+0

我沒有問題如果數據庫有任何重複值。但我希望ArrayList能很好地增加值。 –

+0

這就是當你不正確製造listitem視圖時listview是如何工作的。它根本與arraylist無關。 – Hector

回答

0

在bindView方法中填充該數組並不是一個好主意。 Android不會爲列表中的每一行創建單獨的視圖,而是利用已創建的視圖,這就是爲什麼您總是會在您的數組列表中獲得意外結果的原因。更好的做法是在你的活動中填充數組,而不是適配器。只需查詢您的數據庫,以獲得相同的結果,如下所示:

Cursor cursor = getContentResolver().query(
    uri, 
    projection,      
    selectionClause     
    selectionArgs,      
    sortOrder); 

while (cursor.moveToNext()){ 
    arrayList.add(cursor.getAsString(cursor.getColumnIndex('column_name'))); 
} 
cursor.close() 
+0

我在回答之前解決了問題。你是對的。感謝您的回答。 –