当前位置:网站首页>idea使用jdbc对数据库进行增删改查,以及使用懒汉方式实现单例模式
idea使用jdbc对数据库进行增删改查,以及使用懒汉方式实现单例模式
2022-08-02 14:18:00 【Wsy286047981】
如果今后更改了数据库的类型,它的sql语句会变,所以使用了连接接口的方式来写,以便于今后更改数据库之后依然可以使用
这是接口的类的代码
package news;
import javax.xml.crypto.Data;
import java.sql.*;
public interface news2 {
public void addNews(int id,int categoryid,String title,String summary,String content,Date createDate);
public void updateNews(int id,String title);
public void deleteNews(int id);
public void getNewsByTitle(String title);
}
然后需要让实现了这个接口的实现类继承一个写了增删改查具体方法的类
这是写了具体方法需要被继承的类的代码
package news;
import sun.security.mscapi.CPublicKey;
import tool.util.ConfigManager;
import java.sql.*;
public class BaseDao {
Connection connection = null;
PreparedStatement pstmt = null;
ResultSet result = null;
public boolean getConnection(){
try {
// 在另一个工具类中读取配置文件中的配置信息
String url = (ConfigManager.getInstance().getString("jdbc.connection.url"));
String userName = (ConfigManager.getInstance().getString("jdbc.connection.userName"));
String password =(ConfigManager.getInstance().getString("jdbc.connection.password"));
connection = DriverManager.getConnection(url, userName, password );
}catch (Exception e){
System.err.println("出错了");
return false;
}
return true;
}
//String sql="update kgcnews.news_detail set title=? where id=?";
public int executeUpdate(String sql,Object[] paramas){
int updateRows=0;
if (this.getConnection()){
try {
pstmt = connection.prepareStatement(sql);
for (int i=0;i<paramas.length;i++){
pstmt.setObject(i+1,paramas[i]);
}
updateRows=pstmt.executeUpdate();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
}
return updateRows;
}
public ResultSet executeSQL(String sql,Object[] paramas) {
if (this.getConnection()) {
try {
pstmt = connection.prepareStatement(sql);
for (int i = 0; i < paramas.length; i++) {
pstmt.setObject(i + 1, paramas[i]);
}
result = pstmt.executeQuery();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
}
return result;
}
public boolean closeResource() {
if (result != null) {
try {
result.close();
} catch (SQLException throwables) {
throwables.printStackTrace();
return false;
}
}
if (pstmt != null) {
try {
pstmt.close();
} catch (SQLException throwables) {
throwables.printStackTrace();
return false;
}
}
if (connection!=null){
try {
connection.close();
} catch (SQLException throwables) {
throwables.printStackTrace();
return false;
}
}
return true;
}
}
接下来是继承了拥有具体方法的类并且实现了接口方法的类的类代码
package news;
import java.sql.*;
public class news2Impl extends BaseDao implements news2{
public void getAll(){
try {
String sql = "select id,categoryid,title,summary,createdate from kgcnews.news_detail";
Object[] pramas = {};
ResultSet result=this.executeSQL(sql,pramas);
while (result.next()) {
// int id=result.getInt(1);
//也可以写列名
int id = result.getInt("id");
// String title=result.getString(2);
String newsTitle = result.getString("title");
int categoryid = result.getInt("categoryid");
String summary = result.getString("summary");
Timestamp createdate = result.getTimestamp("createdate");
System.out.println(id + "\t" + newsTitle + "\t" + categoryid + "\t" + summary + "\t" + createdate);
}
}catch (Exception e){
}
}
public void addNews(int id,int categoryid,String title,String summary,String content,Date createDate){
String sql="insert into kgcnews.news_detail(id,categoryid,title,summary,content,createDate) values(?,?,?,?,?,?)";
Object[] params={id,categoryid,title,summary,content,new Timestamp(createDate.getTime())};
int i=this.executeUpdate(sql,params);
if (i>0){
System.out.println("插入成功");
}
this.closeResource();
}
public void updateNews(int id,String title){
String sql="update kgcnews.news_detail set title=? where id=?";
Object[] params={title,id};
int i=this.executeUpdate(sql,params);
if (i>0){
System.out.println("删除成功");
}
this.closeResource();
}
public void deleteNews(int id){
String sql="delete from kgcnews.news_detail where id=?";
Object[] params={id};
int i=this.executeUpdate(sql,params);
if (i>0){
System.out.println("删除成功");
}
this.closeResource();
}
public void getNewsByTitle(String title){
try {
String sql = "select id,title from kgcnews.news_detail where title=?";
Object[] params={};
ResultSet result=this.executeSQL(sql,params);
while (result.next()) {
// int id=result.getInt(1);
//也可以写列名
int id = result.getInt("id");
// String title=result.getString(2);
String newsTitle = result.getString("title");
System.out.println(id + "\t" + newsTitle);
}
}catch (Exception e){
}finally {
this.closeResource();
}
}
public static void main(String[] args) {
news2Impl n=new news2Impl();
n.getAll();
}
}
因为不同的用户登录时用户名不同,用户密码不同,或者数据库类型不同会导致url,username,password的不同,所以可以设置一个配置文件,配置文件需要在src文件夹下创建(后缀名为properties),配置文件的结构是键值对,然后用key value的形式在配置文件里写入相关信息
需要注意的是,在连接数据库之前一般都需要加载该数据库产商提供的驱动(一个jar包里面),加载驱动使用的方法是Class.forName(String),String填的就是引入的jar包里Driver类的路径
但是高版本的Oracle和MySql就不用加载驱动类了,加载了反而会报错,所以这里我虽然也写了driver但是没有用到
如何获取这个配置文件里的键值对信息然后给它弄到connection创建时里面的三个参数里呢?
这时候可以创建一个工具类来对配置文件进行一个读
因为IO比较耗资源,所以让用户只能创建一个该类的对象来读,所以可以采用单例模式
把构造方法给private了,然后用一个静态方法来给用户return对象(使用static让用户不能创建对象的时候也能访问这个类的方法)
这里用到的是懒汉方式,也就是调用getInstance()这个静态方法时才会创建这个configManager对象,这种方法有个弊端是,当多线程操作时可能会议由多个线程进入这个方法,会导致多线程的不安全,所以可以用synchronized给它上一个锁
package tool.util;
import com.sun.deploy.panel.IProperty;
import java.io.IOException;
import java.io.InputStream;
import java.util.Properties;
//工具类,拿来读属性文件
public class ConfigManager {
private Properties p=new Properties();
/*因为读取config文件是io,很耗资源,所以为了不让别人直接new这个类,所以要先给它私有
要让程序给用户唯一一个对象,所以后面要定义一个static方法
* */
private ConfigManager(){
//配置文件的文件名,这个配置文件一定要放在src下边
String configFile="Datebase.properties";
//这个getResourceAsStream可以把一个资源读进来变成一个流
InputStream in =ConfigManager.class.getClassLoader().getResourceAsStream(configFile);
try {
//把属性文件的输入流in通过p的load方法搞到p对象里面去,因为p有相应方法可以读属性文件
p.load(in);
//load到p对象里去以后这个in就可以close了
in.close();
} catch (IOException e) {
e.printStackTrace();
}
}
//这是用户将有的唯一一个ConfigManager对象
private static ConfigManager configManager=null;
/*提供给用户一个唯一的ConfigManager对象,为了方便别人在不newreturn configManager;对象的同时能够调用这个方法
* 所以将这个方法定义为静态的static
* 这是单例中的饿汉方式,会出现多线程不安全的问题,所以要用synchronized上锁
* */
public static synchronized ConfigManager getInstance(){
if (configManager==null){
configManager=new ConfigManager();
return configManager;
}
return configManager;
}
//根据属性文件中的键获得对应的值
public String getString(String key){
//p的方法:因为properties文件里的本质是键值对,所以给它一个键就可以返回对应的值
return p.getProperty(key);
}
}
若是使用饿汉方式就在方法外就创建完该对象,然后方法里直接return就行
边栏推荐
猜你喜欢
随机推荐
【路由器与交换机的作用与特点 】
【SVM回归预测】基于LibSVM实现多特征数据的预测
web渗透之文件上传漏洞
Mysql理解MVCC与BufferPool缓存机制
How to tick the word box?
OpenPose command line
解决跨域问题的方法 --- CORS
JMM&synchronized&volatile详解
velocity模板页面四则运算
Cmd Markdown Formula Guidebook
华为Vlan创建及原理简单说明
Spark的概念、特点、应用场景
这几年让你大呼惊人的AI应用,都离不开这项技术
CPU缓存一致性协议MESI
【软件测试】测试基础讲解
华为单臂路由配置,实现不同vlan之间的通信
对象头和synchronized的升级
关于机组的部分知识点随笔
appium 报错:AttributeError:
grub 命令使用