个人博客地址
《数据库系统概论》课程之实验六 通过嵌入式SQL访问数据库
1 实验目的
熟悉通过嵌入式SQL(主语言为JAVA语言)编程访问数据库
2 实验平台和实验工具
在MySQL数据库管理系统上,通过Java语言编写访问数据库的应用程序来对数据库进行各种数据操作。
编程工具:IDEA 2022.1
3 实验内容和要求
通过嵌入式SQL编程访问数据库的基本步骤
对学生课程数据库中的表,完成下面功能(你也可以自己给出功能要求):
- 查询某一门课程的信息。要查询的课程由用户在程序运行过程中指定,放在主变量中。
- 查询选修某一门课程的选课信息,要查询的课程号由用户在程序运行过程中指定,放在主变量中,然后根据用户的要求修改其中某些记录的成绩字段。
代码设计思路:
- 通过基于jdbc驱动的数据库C3P0连接池,实现与数据库的连接。
- 使用Statement接口用于执行静态的SQL语句。
- 使用PreparedStatement接口,结合占位符?,执行含参的SQL语句。
- 使用ResultSet保存查询结果。
主要类和函数如下
C3P0Util类:
public static Connection getConnection()
:通过C3P0连接池与数据库建立连接public static void release(Connection conn)
:释放连接回连接池
CourseDao类:
public static void showCname()
:查询课程号、课程名,以给用户选择public static void QueryOne(Integer Cno)
:查询某一门课程的信息,变量为课程号Cno
SCDao类:
public static void QueryOne(Integer Cno)
:查询选修某一门课程的选课信息,变量为课程号Cnopublic static void UpdateOne(String Sno, Integer Cno, Integer Grade)
:根据用户的要求修改其中某些记录的成绩字段,变量为学号Sno,课程号Cno,成绩Grade
run类:
public static void main(String[] args)
:主函数实现功能逻辑
4 实验结果
代码运行结果如下:
主页面
查询某一门课程的信息
查询选修某一门课程的选课信息
修改其中某些记录的成绩字段
实验心得
通过这次实验,我掌握了如何Java语言编写访问数据库管理系统MySQL,来对数据库进行各种数据操作。有以下几点需要注意:
-
数据库查询的接口
Statement
可用于执行固定的SQL语句。执行函数executeUpdate()
用于执行增、删、改等SQL语句,而executeQuery()
用于执行查询语句,对于Statement
,需要加上SQL语句作为参数。 -
PreparedStatement
继承了Statement
,但它在通过Connection
的类函数prepareStatement
定义时就已经预编译,参数SQL语句中可以含有?
作为占位符,后续用于填充变量。完成变量填入后,在executeUpdate()
或executeQuery()
中就不需要以SQL语句作为参数。 -
查询的返回结果将保存在
ResultSet
类的变量中。若要遍历读取该结果,则需要在定义数据库查询接口时加入2个参数:TYPE_SCROLL_INSENSITIVE
:游标双向滚动,但不及时更新;CONCUR_READ_ONLY
:只读 -
C3P0
封装了jdbc
对DataSource
接口的实现,本实验正是通过C3P0
连接池实现了对MySQL数据库的连接。需要额外注意,当建立连接后,若长时间未使用该连接,要及时将连接释放回连接池,并在连接释放前通过close()
把Statement
、PrepareStatement
、ResultSet
的资源释放。
附 关键代码
与数据库连接
public class C3P0Util {
//c3p0封装了jdbc对DataSource接口的实现
private static DataSource dataSource = new ComboPooledDataSource();
//从连接池中获取连接
public static Connection getConnection() {
try {
//返回连接
return dataSource.getConnection();
} catch (SQLException e) {
// TODO Auto-generated catch block
throw new RuntimeException();
}
}
//释放连接回连接池
public static void release(Connection conn) {
if (conn != null) {
try {
conn.close();
} catch (Exception e) {
e.printStackTrace();
}
conn = null;
}
}
}
对数据库进行操作
CourseDao类:
public class CourseDao {
//查询课程号、课程名,以给用户选择
public static void showCname() {
// 建立连接
Connection conn = C3P0Util.getConnection();
// 查询语句
String sql = "select Cno,Cname from Course";
try {
//定义数据库查询的接口(TYPE_SCROLL_INSENSITIVE:游标双向滚动,但不及时更新;CONCUR_READ_ONLY:只读)
Statement stmt = conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY);
//执行查询,得到结果
ResultSet result = stmt.executeQuery(sql);
if (result.first()) {
// 输出表头
System.out.printf("|%-8s|%-16s|\n", "Cno", "Cname");
for (int i = 1; i <= 3 + 8 + 16 + 1; i++) {
System.out.print("-");
}
System.out.print('\n');
// 输出结果
do {
Integer c1 = result.getInt("Cno");
String c2 = result.getString("Cname");
System.out.printf("|%-8d", c1);
System.out.printf("|%-16s", c2);
System.out.print("|\n");
} while (result.next());
for (int i = 1; i <= 3 + 8 + 16 + 1; i++) {
System.out.print("-");
}
System.out.print('\n');
} else {
System.out.println("Course表为空");
}
//释放资源
stmt.close();
result.close();
conn.close();
} catch (Exception e) {
e.printStackTrace();
}
}
//查询某一门课程的信息,变量为课程号Cno
public static void QueryOne(Integer Cno) {
// 建立连接
Connection conn = C3P0Util.getConnection();
// 查询语句,一个变量待定
String sql = "select * from Course where Cno = ?";
try {
// 预处理接口
PreparedStatement pstmt = conn.prepareStatement(sql,ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY); // 结果集的游标可以上下移动
// 填入变量
pstmt.setInt(1, Cno);
//执行查询,得到结果
ResultSet result = pstmt.executeQuery();
if (result.first()) {
// 输出表头
System.out.printf("|%-8s|%-16s|%-8s|%-8s|\n", "Cno", "Cname", "Cpn", "Ccredit");
for (int i = 1; i <= 5 + 8 * 3 + 16 + 1; i++) {
System.out.print("-");
}
System.out.print('\n');
// 输出结果
do {
Integer c1 = result.getInt("Cno");
String c2 = result.getString("Cname");
Integer c3 = result.getInt("Cpno");
Integer c4 = result.getInt("Ccredit");
System.out.printf("|%-8d", c1);
System.out.printf("|%-16s", c2);
System.out.printf("|%-8d", c3);
System.out.printf("|%-8d", c4);
System.out.print("|\n");
} while (result.next());
for (int i = 1; i <= 5 + 8 * 3 + 16 + 1; i++) {
System.out.print("-");
}
System.out.print('\n');
} else {
System.out.printf("课程 %s 不存在!\n",Cno);
}
//释放资源
pstmt.close();
result.close();
conn.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}
SCDao类
public class SCDao {
//查询选修某一门课程的选课信息
public static void QueryOne(Integer Cno) {
// 建立连接
Connection conn = C3P0Util.getConnection();
// 查询语句,一个变量待定
String sql = "select * from SC where Cno = ?";
try {
// 预处理接口
PreparedStatement pstmt = conn.prepareStatement(sql, ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY); // 结果集的游标可以上下移动
// 填入变量
pstmt.setInt(1, Cno);
//执行查询,得到结果
ResultSet result = pstmt.executeQuery();
if (result.first()) {
// 输出表头
System.out.printf("课程 %s 的信息如下:\n",Cno);
System.out.printf("|%-16s|%-8s|%-8s|\n", "Sno", "Cno", "Grade");
for (int i = 1; i <= 4 + 8 * 2 + 16 + 1; i++) {
System.out.print("-");
}
System.out.print('\n');
// 输出结果
do {
String c1 = result.getString("Sno");
Integer c2 = result.getInt("Cno");
Integer c3 = result.getInt("Grade");
System.out.printf("|%-16s", c1);
System.out.printf("|%-8d", c2);
System.out.printf("|%-8d", c3);
System.out.print("|\n");
} while (result.next());
for (int i = 1; i <= 4 + 8 * 3 + 16 + 1; i++) {
System.out.print("-");
}
System.out.print('\n');
} else {
System.out.printf("课程 %s 不存在!\n",Cno);
}
//释放资源
pstmt.close();
result.close();
conn.close();
} catch (Exception e) {
e.printStackTrace();
}
}
// 根据用户的要求修改其中某些记录的成绩字段
public static void UpdateOne(String Sno, Integer Cno, Integer Grade) {
// 建立连接
Connection conn = C3P0Util.getConnection();
// 查询语句,一个变量待定
String sql = "update SC set Grade = ? where Sno = ? and Cno = ?";
try {
// 预处理接口
PreparedStatement pstmt = conn.prepareStatement(sql);
// 填入变量
pstmt.setInt(1, Grade);
pstmt.setString(2,Sno);
pstmt.setInt(3,Cno);
//执行sql语句,得到结果
int result = pstmt.executeUpdate();
//没有查询结果
if(result==0)
System.out.println("该学生不存在");
else {
System.out.println("更新成功");
// 输出更新后的课程信息
QueryOne(Cno);
}
//释放资源
pstmt.close();
conn.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}
主函数
public class run {
public static void main(String[] args) {
//程序执行状态
boolean flag = true;
//监视输入
Scanner in = new Scanner(System.in);
while (flag) {
//初始界面
System.out.println("请选择要执行的操作:");
System.out.println("1:查询某一门课程的信息");
System.out.println("2:查询选修某一门课程的选课信息/修改某一课程的成绩");
System.out.println("3:退出程序");
//操作
int op = in.nextInt();
if (op == 1) {
// 显示课程号 课程名
CourseDao.showCname();
System.out.println("请在下方选择需要查询的课程编号:");
int Cno = in.nextInt();
CourseDao.QueryOne(Cno);
} else if (op == 2) {
// 显示课程号 课程名
CourseDao.showCname();
System.out.println("请在下方选择需要查询选课信息的课程编号:");
int Cno = in.nextInt();
SCDao.QueryOne(Cno);
System.out.println("是否要修改该课程某一学生的成绩?");
System.out.println("1:是");
System.out.println("其它:返回主页面");
int op2 = in.nextInt();
while (op2 == 1) {
System.out.print("请输入学号:"); //:
String Sno = in.next();
System.out.print("请输入成绩:"); //
int Grade = in.nextInt();
SCDao.UpdateOne(Sno, Cno, Grade);
System.out.println("是否要继续修改该课程某一学生的成绩?"); //
System.out.println("1:是");
System.out.println("其它:返回主页面");
op2 = in.nextInt();
}
} else if (op == 3) {
flag = false;
System.out.println("程序即将退出!");
} else {
System.out.println("请输入正确的命令");
}
}
}
}