无法为非主要列插入相同的ID - Android Sqllite

时间:2015-07-07 03:56:21

标签: android sqlite

我正在尝试将一些值插入到我的visits表中。访问表有一个schedule_id列,它保存一个整数值。

Schedule_id不是主键。

我的问题是当我尝试在Schedule_id列中插入相同的id时,我收到并且错误。

但如果我尝试使用唯一值,那就有效。

这是我的代码。

Dbhelper课程

public class DBHelper extends SQLiteOpenHelper {


    public static final String TAG = "DBHelper";

    // columns of the schedule table
    public static final String TABLE_SCHEDULE= "schedule";
    public static final String COLUMN_SCHEDULE_ID = "schedule_id";
    public static final String COLUMN_SCHEDULE_NAME = "schedule_name";
    public static final String COLUMN_SCHEDULE_DATE = "schedule_date";

    // columns of the items table
    public static final String TABLE_ITEM= "items";
    public static final String COLUMN_ITEM_ID = "item_id";
    public static final String COLUMN_ITEM_VISIT_ID = "visit_id";
    public static final String COLUMN_ITEM_NAME = "item_name";
    public static final String COLUMN_ITEM_CHECK_STATUS= "item_check_status";
    public static final String COLUMN_ITEM_COMMENT = "item_comment";


    // columns of the employees table
    public static final String TABLE_VISITS = "visits";
    public static final String COLUMN_VISITS_ID = "visit_id";
    public static final String COLUMN_VISITS_SCHEDULE_ID = "schedule_id";
    public static final String COLUMN_VISITS_NAME = "visit_name";
    public static final String COLUMN_VISITS_TIME = "visit_time";
    public static final String COLUMN_VISITS_PLACE = "visit_place";
    public static final String COLUMN_VISITS_ADDRESS ="visit_address";
    public static final String COLUMN_VISITS_LOCATION_LAT = "visit_location_lat";
    public static final String COLUMN_VISITS_LOCATION_LNG = "visit_location_lng";
    public static final String COLUMN_VISITS_STATUS = "visit_status";

    private static final String DATABASE_NAME = "certisagent";
    private static final int DATABASE_VERSION = 2;

    // SQL statement of the visits table creation
    private static final String SQL_CREATE_TABLE_VISITS = "CREATE TABLE " + TABLE_VISITS + "("
            + COLUMN_VISITS_ID              + " INTEGER PRIMARY KEY, "
            + COLUMN_VISITS_SCHEDULE_ID     + " INTEGER, "
            + COLUMN_VISITS_NAME            + " TEXT NOT NULL, "
            + COLUMN_VISITS_TIME            + " TEXT NOT NULL, "
            + COLUMN_VISITS_PLACE           + " TEXT NOT NULL, "
            + COLUMN_VISITS_ADDRESS         + " TEXT NOT NULL, "
            + COLUMN_VISITS_LOCATION_LAT    + " TEXT NOT NULL, "
            + COLUMN_VISITS_LOCATION_LNG    + " TEXT NOT NULL, "
            + COLUMN_VISITS_STATUS          + " INTEGER "
            +");";


    // SQL statement of the schedule table creation
    private static final String SQL_CREATE_TABLE_SCHEDULE = "CREATE TABLE " + TABLE_SCHEDULE + "("
            + COLUMN_SCHEDULE_ID        + " INTEGER PRIMARY KEY, "
            + COLUMN_SCHEDULE_NAME      + " TEXT NOT NULL, "
            + COLUMN_SCHEDULE_DATE      + " TEXT NOT NULL "
            +");";

    // SQL statement of the item table creation
    private static final String SQL_CREATE_TABLE_ITEMS = "CREATE TABLE " + TABLE_ITEM + "("
            + COLUMN_ITEM_ID            + " INTEGER PRIMARY KEY, "
            + COLUMN_ITEM_VISIT_ID      + " INTEGER, "
            + COLUMN_ITEM_NAME          + " TEXT NOT NULL, "
            + COLUMN_ITEM_CHECK_STATUS  + " INTEGER, "
            + COLUMN_ITEM_COMMENT       + " TEXT NOT NULL "
            +");";

    public DBHelper(Context context) {
        super(context, DATABASE_NAME, null, DATABASE_VERSION);
    }

    @Override
    public void onCreate(SQLiteDatabase database) {
        database.execSQL(SQL_CREATE_TABLE_SCHEDULE);
        database.execSQL(SQL_CREATE_TABLE_VISITS);
        database.execSQL(SQL_CREATE_TABLE_ITEMS);


    }

    @Override
    public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
        Log.w(TAG,
                "Upgrading the database from version " + oldVersion + " to " + newVersion);
        // clear all data
        db.execSQL("DROP TABLE IF EXISTS " + TABLE_SCHEDULE);
        db.execSQL("DROP TABLE IF EXISTS " + TABLE_VISITS);
        db.execSQL("DROP TABLE IF EXISTS " + TABLE_ITEM);

        // recreate the tables
        onCreate(db);
    }

}

VisitsDOA Class

public class VisitsDAO {

    public static final String TAG = "visitsDAO";


    // Database fields
    private SQLiteDatabase mDatabase;
    private DBHelper mDbHelper;
    private Context mContext;
    private String[] mAllColumns = {
            DBHelper.COLUMN_VISITS_ID,
            DBHelper.COLUMN_VISITS_SCHEDULE_ID,
            DBHelper.COLUMN_VISITS_NAME,
            DBHelper.COLUMN_VISITS_TIME,
            DBHelper.COLUMN_VISITS_PLACE,
            DBHelper.COLUMN_VISITS_ADDRESS,
            DBHelper.COLUMN_VISITS_LOCATION_LAT,
            DBHelper.COLUMN_VISITS_LOCATION_LNG,
            DBHelper.COLUMN_VISITS_STATUS  };

    public VisitsDAO(Context context) {
        this.mContext = context;
        mDbHelper = new DBHelper(context);
        // open the database
        try {
            open();
        } catch (SQLException e) {
            Log.e(TAG, "SQLException on openning database " + e.getMessage());
            e.printStackTrace();
        }
    }

    public void open() throws SQLException {
        mDatabase = mDbHelper.getWritableDatabase();
    }

    public void close() {
        mDbHelper.close();
    }

    public Visits createvisits(int vid, int v_sid, String vname, String vtime, String vplace, String address, String vlat, String vlong, int vstatus) {
        ContentValues values = new ContentValues();
        values.put(DBHelper.COLUMN_VISITS_ID, vid);
        values.put(DBHelper.COLUMN_VISITS_SCHEDULE_ID, v_sid);
        values.put(DBHelper.COLUMN_VISITS_NAME, vname);
        values.put(DBHelper.COLUMN_VISITS_TIME, vtime);
        values.put(DBHelper.COLUMN_VISITS_PLACE, vplace);
        values.put(DBHelper.COLUMN_VISITS_ADDRESS, address);
        values.put(DBHelper.COLUMN_VISITS_LOCATION_LAT, vlat);
        values.put(DBHelper.COLUMN_VISITS_LOCATION_LNG, vlong);
        values.put(DBHelper.COLUMN_VISITS_STATUS, vstatus);
        long insertId = mDatabase
                .insert(DBHelper.TABLE_VISITS, null, values);
        Cursor cursor = mDatabase.query(DBHelper.TABLE_VISITS, mAllColumns,
                DBHelper.COLUMN_SCHEDULE_ID + " = " + insertId, null, null,
                null, null);
        cursor.moveToFirst();
        Visits newvisits = cursorTovisits(cursor);
        cursor.close();
        return newvisits;
    }



    public List<Visits> getAllvisits() {
        List<Visits> listVisits = new ArrayList<Visits>();

        Cursor cursor = mDatabase.query(DBHelper.TABLE_VISITS, mAllColumns,
                null, null, null, null, null);
        if (cursor != null) {
            cursor.moveToFirst();
            while (!cursor.isAfterLast()) {
                Visits visits = cursorTovisits(cursor);
                listVisits.add(visits);
                cursor.moveToNext();
            }

            // make sure to close the cursor
            cursor.close();
        }
        return listVisits;
    }

    public List<Visits> getAllvisitsforSchedule(int id) {
        List<Visits> listVisits = new ArrayList<Visits>();

        Cursor cursor = mDatabase.query(DBHelper.TABLE_VISITS, mAllColumns,
                DBHelper.COLUMN_VISITS_SCHEDULE_ID + " = ?",
                new String[]{String.valueOf(id)}, null, null, null);
        if (cursor != null) {
            cursor.moveToFirst();
            while (!cursor.isAfterLast()) {
                Visits visits = cursorTovisits(cursor);
                listVisits.add(visits);
                cursor.moveToNext();
            }

            // make sure to close the cursor

            cursor.close();
        }
        return listVisits;
    }

    public Visits getvisitById(int id) {
        Cursor cursor = mDatabase.query(DBHelper.TABLE_VISITS, mAllColumns,
                DBHelper.COLUMN_VISITS_ID + " = ?",
                new String[]{String.valueOf(id)}, null, null, null);

        if (cursor != null) {
            cursor.moveToFirst();
        }

        Visits visits = cursorTovisits(cursor);
        return visits;
    }

    protected Visits cursorTovisits(Cursor cursor) {
        Visits schedule = new Visits();

        schedule.setvId(cursor.getInt(0));
        schedule.setVschID(cursor.getInt(1));
        schedule.setVname(cursor.getString(2));
        schedule.setVtime(cursor.getString(3));
        schedule.setVplace(cursor.getString(4));
        schedule.setVaddress(cursor.getString(5));
        schedule.setVlat(cursor.getString(6));
        schedule.setVlong(cursor.getString(7));
        schedule.setVstatus(cursor.getInt(8));


        return schedule;

    }

}

主要活动类

public class MainActivity extends ListActivity {

    private static final String TAG = "Main Activity";
    private ScheduleDAO mscheduleDAo;
    private VisitsDAO mvisitsDAO;
    List<Schedule> ListSchedule;

    // schedule variables
    public int schedule_id = 29;
    public String schedule_name = "Schedule 13";
    public String schedule_date = "2015-07-06";


    // visits variables

    public int visit_id = 42;
    public int visit_schedule_id =41;
    public String visit_name = "visit15";
    public String visit_time = "21:23";
    public String visit_place= "kilinochchi";
    public String visit_address = "vavuniya Street";
    public String visit_lat = "0.1115252";
    public String visit_long = "0.254255";
    public int visit_status = 0;


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

      // insert_schedule();
       insert_visits();

        list_all_schedules();
    }

    @Override
    protected void onListItemClick(ListView l, View v, int position, long id) {

        Schedule schdul = ListSchedule.get(position);
        int sch_id = schdul.getId();
        String sch_stng_id =Integer.toString(sch_id);;
        String sch_name = schdul.getName();

        Intent intent = new Intent(this, VisitsActivity.class);
        intent.putExtra("sch_id", schdul.getId());
        intent.putExtra("sch_name", schdul.getName());


        Toast.makeText(this, sch_stng_id+" : "+sch_name, Toast.LENGTH_LONG).show();
        startActivity(intent);
       // super.onListItemClick(l, v, position, id);
    }


    private void list_all_schedules(){

        mscheduleDAo =new ScheduleDAO(getApplicationContext());
        ListSchedule = mscheduleDAo.getAllschedules();

        ArrayAdapter <Schedule> adapter = new ArrayAdapter<Schedule>(this, R.layout.list_schedules_layout, ListSchedule);
        setListAdapter(adapter);
    }


    private boolean insert_schedule(){
        mscheduleDAo =new ScheduleDAO(getApplicationContext());
        Schedule createdschedule = mscheduleDAo.createschedule(Integer.parseInt(String.valueOf(schedule_id)),
                schedule_name,
                schedule_date);
        Toast.makeText(this, "Schedule insert sucessfull", Toast.LENGTH_LONG).show();

        return true;
    }

    private boolean insert_visits(){
        mvisitsDAO = new VisitsDAO(getApplicationContext());
        Visits createvisits =mvisitsDAO.createvisits(Integer.parseInt(String.valueOf(visit_id)),
                Integer.parseInt(String.valueOf(visit_schedule_id)),
                visit_name, visit_time, visit_place, visit_address, visit_lat, visit_long,
                visit_status);
        Toast.makeText(this, "Visit insert sucessfull", Toast.LENGTH_LONG).show();
        return true;
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.menu_main, menu);
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        // Handle action bar item clicks here. The action bar will
        // automatically handle clicks on the Home/Up button, so long
        // as you specify a parent activity in AndroidManifest.xml.
        int id = item.getItemId();

        //noinspection SimplifiableIfStatement
        if (id == R.id.action_settings) {
            return true;
        }

        return super.onOptionsItemSelected(item);
    }
}

错误

07-07 09:11:28.957  11339-11339/lk.db.learn.databsetesting E/AndroidRuntime﹕ FATAL EXCEPTION: main
    Process: lk.db.learn.databsetesting, PID: 11339
    java.lang.RuntimeException: Unable to start activity ComponentInfo{lk.db.learn.databsetesting/lk.db.learn.databsetesting.MainActivity}: android.database.CursorIndexOutOfBoundsException: Index 0 requested, with a size of 0
            at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2429)
            at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2493)
            at android.app.ActivityThread.access$800(ActivityThread.java:166)
            at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1283)
            at android.os.Handler.dispatchMessage(Handler.java:102)
            at android.os.Looper.loop(Looper.java:136)
            at android.app.ActivityThread.main(ActivityThread.java:5584)
            at java.lang.reflect.Method.invokeNative(Native Method)
            at java.lang.reflect.Method.invoke(Method.java:515)
            at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1268)
            at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1084)
            at dalvik.system.NativeStart.main(Native Method)
     Caused by: android.database.CursorIndexOutOfBoundsException: Index 0 requested, with a size of 0
            at android.database.AbstractCursor.checkPosition(AbstractCursor.java:426)
            at android.database.AbstractWindowedCursor.checkPosition(AbstractWindowedCursor.java:136)
            at android.database.AbstractWindowedCursor.getInt(AbstractWindowedCursor.java:68)
            at lk.db.learn.databsetesting.data.VisitsDAO.cursorTovisits(VisitsDAO.java:156)
            at lk.db.learn.databsetesting.data.VisitsDAO.createvisits(VisitsDAO.java:76)
            at lk.db.learn.databsetesting.MainActivity.insert_visits(MainActivity.java:105)
            at lk.db.learn.databsetesting.MainActivity.onCreate(MainActivity.java:59)
            at android.app.Activity.performCreate(Activity.java:5442)
            at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1094)
            at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2393)
            at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2493)
            at android.app.ActivityThread.access$800(ActivityThread.java:166)
            at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1283)
            at android.os.Handler.dispatchMessage(Handler.java:102)
            at android.os.Looper.loop(Looper.java:136)
            at android.app.ActivityThread.main(ActivityThread.java:5584)
            at java.lang.reflect.Method.invokeNative(Native Method)
            at java.lang.reflect.Method.invoke(Method.java:515)
            at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1268)
            at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1084)
            at dalvik.system.NativeStart.main(Native Method)

2 个答案:

答案 0 :(得分:1)

insert()返回插入行的SQLite rowid。根据您的create table语句,此值应与COLUMN_VISITS_ID匹配,而不是COLUMN_VISITS_SCHEDULE_ID。您现在拥有的代码是在错误的列中查找此值。查询找不到匹配的行并返回空光标,因此当您尝试从光标读取时,最终会得到CursorIndexOutOfBoundsException

在VisitsDAO中更改您的查询,如下所示:

long insertId = mDatabase.insert(DBHelper.TABLE_VISITS, null, values);
Cursor cursor = mDatabase.query(DBHelper.TABLE_VISITS, mAllColumns,
        DBHelper.COLUMN_VISITS_ID + " = " + insertId, null, null, null, null);

答案 1 :(得分:1)

cursorTovisits(光标光标)中,请检查光标对象是否有数据。从堆栈跟踪开始,似乎光标没有正确的数据或者没有指向正确的位置。它会抛出这个 CursorIndexOutOfBoundsException 。从docs开始,当光标超出范围时抛出此异常。

要解决此错误,请使用以下内容:

if( cursor != null && cursor.moveToFirst() ){
    num = cursor.getString(cursor.getColumnIndex("column name"));
}