SQLite 如何匹配不同表中的值?
How to match values in different tables in SQLite?
我正在尝试创建一个数据库函数来帮助我匹配我的学生 ID。 table_userinfo 中已经存储了学生 ID、姓名和课程值。 table_users 为空,接受用户的邮箱、学号和密码。我想创建一个函数,只有 table_userinfo 中存储的学生 ID 可以注册,否则显示学生不存在的错误。用户输入的学号也应该从table_userinfo中获取对应的课程和姓名。还有我的代码是否正确插入值。因为我之前尝试过并且在第一个插入值行中出现 运行 错误。
//Code for table creation
public static final String SQL_TABLE_USERS = " CREATE TABLE " +
TABLE_USERS
+ " ( "
+ KEY_ID + " INTEGER PRIMARY KEY, "
+ KEY_EMAIL + " TEXT, "
+ KEY_SID + " INTEGER, "
+ KEY_PASSWORD + " TEXT"
+ " ) ";
//SQL for creating user info table
public static final String SQL_TABLE_USERINFO = " CREATE TABLE "
+ TABLE_USERINFO
+ " ( "
+ KEY_ID + "INTEGER PRIMARY KEY, "
+ KEY_SID + " INTEGER, "
+ KEY_NAME + "TEXT, "
+ KEY_COURSE + " TEXT "
+ " ) ";
public SqliteHelper(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
@Override
public void onCreate(SQLiteDatabase sqLiteDatabase) {
//Create Table when oncreate gets called
sqLiteDatabase.execSQL(SQL_TABLE_USERS);
sqLiteDatabase.execSQL(SQL_TABLE_USERINFO);
sqLiteDatabase.execSQL("INSERT INTO TABLE_USERINFO
VALUES('01','45207160010','Mary James','TYBSCIT')");
sqLiteDatabase.execSQL("INSERT INTO TABLE_USERINFO
VALUES('02','45207160020','Amelia John','FYBCOM')");
更新:-
我现在有两个功能来检查电子邮件是否存在以及学生是否存在于我的 sqlite 代码中。但是,当我从注册页面调用函数时,应用程序崩溃并且日志显示错误出在单击注册按钮时的函数中。我正在分享我的功能和注册页面的代码。如果我犯了一些错误,请告诉我。我已经在我的注册页面上尝试了 for 循环的不同组合。不起作用。但是,如果仅放置电子邮件存在功能,则可以使用。
SQLITE 代码
public boolean ifUserInCourse(String sid) {
boolean rv = false;
String whereclause = KEY_SID + "=?";
String[] whereargs = new String[]{sid};
SQLiteDatabase db = this.getReadableDatabase();
Cursor csr = db.query(TABLE_USERINFO,null, whereclause, whereargs,null,null,null);
if (csr.getCount() > 0) rv = true;
csr.close();
return rv;
}
public boolean isEmailExists(String email) {
SQLiteDatabase db = this.getReadableDatabase();
Cursor cursor = db.query(TABLE_USERS,// Selecting Table
new String[]{KEY_ID, KEY_EMAIL, KEY_SID, KEY_PASSWORD},//Selecting columns want to query
KEY_EMAIL + "=?",
new String[]{email},//Where clause
null, null, null);
if (cursor != null && cursor.moveToFirst()&& cursor.getCount()>0) {
//if cursor has value then in user database there is user associated with this given email so return true
return true;
}
//if email does not exist return false
return false;
}
注册码
buttonRegister.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
if (validate()) {
String Email = editTextEmail.getText().toString();
String SID = editTextSID.getText().toString();
String Password = editTextPassword.getText().toString();
progressBar.setVisibility(View.VISIBLE);
//Check in the database is there any user associated with this email
if (!sqliteHelper.ifUserInCourse(SID) && !sqliteHelper.isEmailExists(Email)) {
sqliteHelper.addUser(new User(null, Email, SID, Password));
Snackbar.make(buttonRegister, "User created successfully! Please Login ", Snackbar.LENGTH_LONG).show();
new Handler().postDelayed(new Runnable() {
@Override
public void run() {
finish();
}
}, Snackbar.LENGTH_LONG);
} else {
if(sqliteHelper.isEmailExists(Email)) {
Snackbar.make(buttonRegister, "Email already exists ", Snackbar.LENGTH_LONG).show();
} else {
Snackbar.make(buttonRegister, "User doesn't exists ", Snackbar.LENGTH_LONG).show();
}
}
progressBar.setVisibility(View.GONE);
}
}
});
根据 :-
第 1 期
Also is my code for inserting values right or not. Because i tried it
before and i got a run error in the first insert value line.
除非你有 public static final String TABLE_USERINFO = "TABLE_USERINFO";
考虑到问题的近乎重复,否则你不会
sqLiteDatabase.execSQL("INSERT INTO TABLE_USERINFO VALUES('01','45207160010','Mary James','TYBSCIT')");
sqLiteDatabase.execSQL("INSERT INTO TABLE_USERINFO VALUES('02','45207160020','Amelia John','FYBCOM')");
将因table未找到而导致异常。
我相信你应该使用 :-
sqLiteDatabase.execSQL("INSERT INTO " + TABLE_USERINFO + " VALUES('01','45207160010','Mary James','TYBSCIT')");
sqLiteDatabase.execSQL("INSERT INTO " + TABLE_USERINFO + " VALUES('02','45207160020','Amelia John','FYBCOM')");
- 即使用变量 TABLE_USERINFO 而不是硬编码值 TABLE_USERINFO.
此外,您会遇到问题,因为您使用 + KEY_NAME + "TEXT, "
而不是 + KEY_NAME + " TEXT, "
(省略 space)。
根据 :-
第 2 期
I want to create a function where only the student id stored in
table_userinfo can register, otherwise show an error that student
doesn't exists. The student id inputted by the user should also
retrieve the corresponding course and name from table_userinfo.
以下 SqliteHelper.java 将有助于上述(考虑到您对之前针对类似问题提供的答案的回答)
public class SqliteHelper extends SQLiteOpenHelper {
public static final String DATABASE_NAME = "mydb";
public static final int DATABASE_VERSION = 1;
public static final String TABLE_USERS = "user_reg";
public static final String TABLE_USERINFO = "user_info";
public static final String KEY_ID = BaseColumns._ID;
public static final String KEY_EMAIL = "email";
public static final String KEY_SID = "sid";
public static final String KEY_PASSWORD = "password";
public static final String KEY_NAME = "name";
public static final String KEY_COURSE = "coures";
public static final String SQL_TABLE_USERS = " CREATE TABLE " +
TABLE_USERS
+ " ( "
+ KEY_ID + " INTEGER PRIMARY KEY, "
+ KEY_EMAIL + " TEXT, "
+ KEY_SID + " INTEGER, "
+ KEY_PASSWORD + " TEXT"
+ " ) ";
//SQL for creating user info table
public static final String SQL_TABLE_USERINFO = " CREATE TABLE "
+ TABLE_USERINFO
+ " ( "
+ KEY_ID + "INTEGER PRIMARY KEY, "
+ KEY_SID + " INTEGER, "
+ KEY_NAME + " TEXT, "
+ KEY_COURSE + " TEXT "
+ " ) ";
public SqliteHelper(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
@Override
public void onCreate(SQLiteDatabase sqLiteDatabase) {
//Create Table when oncreate gets called
sqLiteDatabase.execSQL(SQL_TABLE_USERS);
sqLiteDatabase.execSQL(SQL_TABLE_USERINFO);
sqLiteDatabase.execSQL("INSERT INTO " + TABLE_USERINFO + " VALUES('01','45207160010','Mary James','TYBSCIT')");
sqLiteDatabase.execSQL("INSERT INTO " + TABLE_USERINFO + " VALUES('02','45207160020','Amelia John','FYBCOM')");
}
@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
}
public long registerUser(String sid, String email, String password) {
if (email.length() < 1) return -9999;
if (password.length() < 1) return -9998;
if (sid.length() < 1) return -9997;
if (ifUserRegistered(sid)) return -99; // Check if user is already registered
if (!ifUserInCourse(sid)) return -999; // Check if user is enrolled in a course perhpas optional
ContentValues cv = new ContentValues();
cv.put(KEY_SID,sid);
cv.put(KEY_EMAIL,email);
cv.put(KEY_PASSWORD,password);
SQLiteDatabase db = this.getWritableDatabase();
return db.insert(TABLE_USERS,null,cv);
}
public boolean ifUserRegistered(String sid) {
boolean rv = false;
String whereclause = KEY_SID + "=?";
String[] whereargs = new String[]{sid};
SQLiteDatabase db = this.getWritableDatabase();
Cursor csr = db.query(TABLE_USERS,null,whereclause,whereargs,null,null,null);
if (csr.getCount() > 0) rv = true;
csr.close();
return rv;
}
public boolean ifUserInCourse(String sid) {
boolean rv = false;
String whereclause = KEY_SID + "=?";
String[] whereargs = new String[]{sid};
SQLiteDatabase db = this.getWritableDatabase();
Cursor csr = db.query(TABLE_USERINFO,null,whereclause,whereargs,null,null,null);
if (csr.getCount() > 0) rv = true;
csr.close();
return rv;
}
public String getUserNameFromSID(String sid) {
String rv = "";
String whereclause = KEY_SID + "=?";
String[] whereargs = new String[]{sid};
SQLiteDatabase db = this.getWritableDatabase();
Cursor csr = db.query(TABLE_USERINFO,null,whereclause,whereargs,null,null,null);
if (csr.moveToFirst()) {
rv = csr.getString(csr.getColumnIndex(KEY_NAME));
}
csr.close();
return rv;
}
public String getUserCourseFromSID(String sid) {
String rv = "";
String whereclause = KEY_SID + "=?";
String[] whereargs = new String[]{sid};
SQLiteDatabase db = this.getWritableDatabase();
Cursor csr = db.query(TABLE_USERINFO,null,whereclause,whereargs,null,null,null);
if (csr.moveToFirst()) {
rv = csr.getString(csr.getColumnIndex(KEY_COURSE));
}
csr.close();
return rv;
}
}
测试
以上是在 activity 中使用以下代码测试的:-
public class MainActivity extends AppCompatActivity {
SqliteHelper mSQLHlpr;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mSQLHlpr = new SqliteHelper(this);
long result1 = mSQLHlpr.registerUser("010101010101010101","blah@mail.com","1234567890");
long result2 = mSQLHlpr.registerUser("45207160010","xxxx@mail.com","1234567890");
long result3 = mSQLHlpr.registerUser("45207160010","yyyy@mail.com","1234567890");
Log.d(
"RESULTS",
"\tFirst attempt returned " + String.valueOf(result1) + " " + String.valueOf((result1 > 0)) +
"\n\tSecond attempt returned " + String.valueOf(result2) + " " + String.valueOf(result2 > 0) +
"\n\tThird attempt returned " + String.valueOf(result3) + " " + String.valueOf(result3 > 0)
);
String testsid = "45207160010";
Log.d(
"USERBYSID",
"SID " + testsid + " " +
"Has a name of " + mSQLHlpr.getUserNameFromSID(testsid) +
" and a Course of " + mSQLHlpr.getUserNameFromSID(testsid)
);
}
}
- 注意以上内容用于测试目的,不适用于实际的应用程序,因为结果可能会因行已经存在而造成混淆。
结果
以上产生了以下相关输出:-
2019-02-05 12:38:08.684 21533-21533/? D/RESULTS: First attempt returned -999 false
Second attempt returned 1 true
Third attempt returned -99 false
2019-02-05 12:38:08.686 21533-21533/? D/USERBYSID: SID 45207160010 Has a name of Mary James and a Course of Mary James
- -999 是 SID 不存在的代码
- 1 为正表示该行已成功插入,因此所有测试均已通过。
- -99为已注册SID的代码
我正在尝试创建一个数据库函数来帮助我匹配我的学生 ID。 table_userinfo 中已经存储了学生 ID、姓名和课程值。 table_users 为空,接受用户的邮箱、学号和密码。我想创建一个函数,只有 table_userinfo 中存储的学生 ID 可以注册,否则显示学生不存在的错误。用户输入的学号也应该从table_userinfo中获取对应的课程和姓名。还有我的代码是否正确插入值。因为我之前尝试过并且在第一个插入值行中出现 运行 错误。
//Code for table creation
public static final String SQL_TABLE_USERS = " CREATE TABLE " +
TABLE_USERS
+ " ( "
+ KEY_ID + " INTEGER PRIMARY KEY, "
+ KEY_EMAIL + " TEXT, "
+ KEY_SID + " INTEGER, "
+ KEY_PASSWORD + " TEXT"
+ " ) ";
//SQL for creating user info table
public static final String SQL_TABLE_USERINFO = " CREATE TABLE "
+ TABLE_USERINFO
+ " ( "
+ KEY_ID + "INTEGER PRIMARY KEY, "
+ KEY_SID + " INTEGER, "
+ KEY_NAME + "TEXT, "
+ KEY_COURSE + " TEXT "
+ " ) ";
public SqliteHelper(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
@Override
public void onCreate(SQLiteDatabase sqLiteDatabase) {
//Create Table when oncreate gets called
sqLiteDatabase.execSQL(SQL_TABLE_USERS);
sqLiteDatabase.execSQL(SQL_TABLE_USERINFO);
sqLiteDatabase.execSQL("INSERT INTO TABLE_USERINFO
VALUES('01','45207160010','Mary James','TYBSCIT')");
sqLiteDatabase.execSQL("INSERT INTO TABLE_USERINFO
VALUES('02','45207160020','Amelia John','FYBCOM')");
更新:- 我现在有两个功能来检查电子邮件是否存在以及学生是否存在于我的 sqlite 代码中。但是,当我从注册页面调用函数时,应用程序崩溃并且日志显示错误出在单击注册按钮时的函数中。我正在分享我的功能和注册页面的代码。如果我犯了一些错误,请告诉我。我已经在我的注册页面上尝试了 for 循环的不同组合。不起作用。但是,如果仅放置电子邮件存在功能,则可以使用。
SQLITE 代码
public boolean ifUserInCourse(String sid) {
boolean rv = false;
String whereclause = KEY_SID + "=?";
String[] whereargs = new String[]{sid};
SQLiteDatabase db = this.getReadableDatabase();
Cursor csr = db.query(TABLE_USERINFO,null, whereclause, whereargs,null,null,null);
if (csr.getCount() > 0) rv = true;
csr.close();
return rv;
}
public boolean isEmailExists(String email) {
SQLiteDatabase db = this.getReadableDatabase();
Cursor cursor = db.query(TABLE_USERS,// Selecting Table
new String[]{KEY_ID, KEY_EMAIL, KEY_SID, KEY_PASSWORD},//Selecting columns want to query
KEY_EMAIL + "=?",
new String[]{email},//Where clause
null, null, null);
if (cursor != null && cursor.moveToFirst()&& cursor.getCount()>0) {
//if cursor has value then in user database there is user associated with this given email so return true
return true;
}
//if email does not exist return false
return false;
}
注册码
buttonRegister.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
if (validate()) {
String Email = editTextEmail.getText().toString();
String SID = editTextSID.getText().toString();
String Password = editTextPassword.getText().toString();
progressBar.setVisibility(View.VISIBLE);
//Check in the database is there any user associated with this email
if (!sqliteHelper.ifUserInCourse(SID) && !sqliteHelper.isEmailExists(Email)) {
sqliteHelper.addUser(new User(null, Email, SID, Password));
Snackbar.make(buttonRegister, "User created successfully! Please Login ", Snackbar.LENGTH_LONG).show();
new Handler().postDelayed(new Runnable() {
@Override
public void run() {
finish();
}
}, Snackbar.LENGTH_LONG);
} else {
if(sqliteHelper.isEmailExists(Email)) {
Snackbar.make(buttonRegister, "Email already exists ", Snackbar.LENGTH_LONG).show();
} else {
Snackbar.make(buttonRegister, "User doesn't exists ", Snackbar.LENGTH_LONG).show();
}
}
progressBar.setVisibility(View.GONE);
}
}
});
根据 :-
第 1 期Also is my code for inserting values right or not. Because i tried it before and i got a run error in the first insert value line.
除非你有 public static final String TABLE_USERINFO = "TABLE_USERINFO";
考虑到问题的近乎重复,否则你不会
sqLiteDatabase.execSQL("INSERT INTO TABLE_USERINFO VALUES('01','45207160010','Mary James','TYBSCIT')");
sqLiteDatabase.execSQL("INSERT INTO TABLE_USERINFO VALUES('02','45207160020','Amelia John','FYBCOM')");
将因table未找到而导致异常。
我相信你应该使用 :-
sqLiteDatabase.execSQL("INSERT INTO " + TABLE_USERINFO + " VALUES('01','45207160010','Mary James','TYBSCIT')");
sqLiteDatabase.execSQL("INSERT INTO " + TABLE_USERINFO + " VALUES('02','45207160020','Amelia John','FYBCOM')");
- 即使用变量 TABLE_USERINFO 而不是硬编码值 TABLE_USERINFO.
此外,您会遇到问题,因为您使用 + KEY_NAME + "TEXT, "
而不是 + KEY_NAME + " TEXT, "
(省略 space)。
根据 :-
第 2 期I want to create a function where only the student id stored in table_userinfo can register, otherwise show an error that student doesn't exists. The student id inputted by the user should also retrieve the corresponding course and name from table_userinfo.
以下 SqliteHelper.java 将有助于上述(考虑到您对之前针对类似问题提供的答案的回答)
public class SqliteHelper extends SQLiteOpenHelper {
public static final String DATABASE_NAME = "mydb";
public static final int DATABASE_VERSION = 1;
public static final String TABLE_USERS = "user_reg";
public static final String TABLE_USERINFO = "user_info";
public static final String KEY_ID = BaseColumns._ID;
public static final String KEY_EMAIL = "email";
public static final String KEY_SID = "sid";
public static final String KEY_PASSWORD = "password";
public static final String KEY_NAME = "name";
public static final String KEY_COURSE = "coures";
public static final String SQL_TABLE_USERS = " CREATE TABLE " +
TABLE_USERS
+ " ( "
+ KEY_ID + " INTEGER PRIMARY KEY, "
+ KEY_EMAIL + " TEXT, "
+ KEY_SID + " INTEGER, "
+ KEY_PASSWORD + " TEXT"
+ " ) ";
//SQL for creating user info table
public static final String SQL_TABLE_USERINFO = " CREATE TABLE "
+ TABLE_USERINFO
+ " ( "
+ KEY_ID + "INTEGER PRIMARY KEY, "
+ KEY_SID + " INTEGER, "
+ KEY_NAME + " TEXT, "
+ KEY_COURSE + " TEXT "
+ " ) ";
public SqliteHelper(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
@Override
public void onCreate(SQLiteDatabase sqLiteDatabase) {
//Create Table when oncreate gets called
sqLiteDatabase.execSQL(SQL_TABLE_USERS);
sqLiteDatabase.execSQL(SQL_TABLE_USERINFO);
sqLiteDatabase.execSQL("INSERT INTO " + TABLE_USERINFO + " VALUES('01','45207160010','Mary James','TYBSCIT')");
sqLiteDatabase.execSQL("INSERT INTO " + TABLE_USERINFO + " VALUES('02','45207160020','Amelia John','FYBCOM')");
}
@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
}
public long registerUser(String sid, String email, String password) {
if (email.length() < 1) return -9999;
if (password.length() < 1) return -9998;
if (sid.length() < 1) return -9997;
if (ifUserRegistered(sid)) return -99; // Check if user is already registered
if (!ifUserInCourse(sid)) return -999; // Check if user is enrolled in a course perhpas optional
ContentValues cv = new ContentValues();
cv.put(KEY_SID,sid);
cv.put(KEY_EMAIL,email);
cv.put(KEY_PASSWORD,password);
SQLiteDatabase db = this.getWritableDatabase();
return db.insert(TABLE_USERS,null,cv);
}
public boolean ifUserRegistered(String sid) {
boolean rv = false;
String whereclause = KEY_SID + "=?";
String[] whereargs = new String[]{sid};
SQLiteDatabase db = this.getWritableDatabase();
Cursor csr = db.query(TABLE_USERS,null,whereclause,whereargs,null,null,null);
if (csr.getCount() > 0) rv = true;
csr.close();
return rv;
}
public boolean ifUserInCourse(String sid) {
boolean rv = false;
String whereclause = KEY_SID + "=?";
String[] whereargs = new String[]{sid};
SQLiteDatabase db = this.getWritableDatabase();
Cursor csr = db.query(TABLE_USERINFO,null,whereclause,whereargs,null,null,null);
if (csr.getCount() > 0) rv = true;
csr.close();
return rv;
}
public String getUserNameFromSID(String sid) {
String rv = "";
String whereclause = KEY_SID + "=?";
String[] whereargs = new String[]{sid};
SQLiteDatabase db = this.getWritableDatabase();
Cursor csr = db.query(TABLE_USERINFO,null,whereclause,whereargs,null,null,null);
if (csr.moveToFirst()) {
rv = csr.getString(csr.getColumnIndex(KEY_NAME));
}
csr.close();
return rv;
}
public String getUserCourseFromSID(String sid) {
String rv = "";
String whereclause = KEY_SID + "=?";
String[] whereargs = new String[]{sid};
SQLiteDatabase db = this.getWritableDatabase();
Cursor csr = db.query(TABLE_USERINFO,null,whereclause,whereargs,null,null,null);
if (csr.moveToFirst()) {
rv = csr.getString(csr.getColumnIndex(KEY_COURSE));
}
csr.close();
return rv;
}
}
测试
以上是在 activity 中使用以下代码测试的:-
public class MainActivity extends AppCompatActivity {
SqliteHelper mSQLHlpr;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mSQLHlpr = new SqliteHelper(this);
long result1 = mSQLHlpr.registerUser("010101010101010101","blah@mail.com","1234567890");
long result2 = mSQLHlpr.registerUser("45207160010","xxxx@mail.com","1234567890");
long result3 = mSQLHlpr.registerUser("45207160010","yyyy@mail.com","1234567890");
Log.d(
"RESULTS",
"\tFirst attempt returned " + String.valueOf(result1) + " " + String.valueOf((result1 > 0)) +
"\n\tSecond attempt returned " + String.valueOf(result2) + " " + String.valueOf(result2 > 0) +
"\n\tThird attempt returned " + String.valueOf(result3) + " " + String.valueOf(result3 > 0)
);
String testsid = "45207160010";
Log.d(
"USERBYSID",
"SID " + testsid + " " +
"Has a name of " + mSQLHlpr.getUserNameFromSID(testsid) +
" and a Course of " + mSQLHlpr.getUserNameFromSID(testsid)
);
}
}
- 注意以上内容用于测试目的,不适用于实际的应用程序,因为结果可能会因行已经存在而造成混淆。
结果
以上产生了以下相关输出:-
2019-02-05 12:38:08.684 21533-21533/? D/RESULTS: First attempt returned -999 false
Second attempt returned 1 true
Third attempt returned -99 false
2019-02-05 12:38:08.686 21533-21533/? D/USERBYSID: SID 45207160010 Has a name of Mary James and a Course of Mary James
- -999 是 SID 不存在的代码
- 1 为正表示该行已成功插入,因此所有测试均已通过。
- -99为已注册SID的代码