【发布时间】:2014-06-16 08:12:52
【问题描述】:
关于以下问题,我需要您的帮助: 我有两个线程。
第一个线程:应该使用 Scanner 类从标准输入读取用户输入
扫描仪扫描仪=新的扫描仪(System.in);
并且正在等待整个字符串。该线程首先获得到方法 next()。
第二个线程在之后到达并尝试使用 jdbc - odbc 打开连接。
connection = DriverManager.getConnection("jdbc:odbc:baza");
发生的是方法 getConnection() 和第二个线程被第一个阻塞。我的问题是为什么会这样?我怎样才能防止这种情况?
我已经从我的项目中创建了小代码,所以它更容易阅读..
我感兴趣的另一件事是为什么
Class.forName("sun.jdbc.odbc.JdbcOdbcDriver");
是可选的。我的程序有无它都可以工作吗? java默认加载驱动吗?
代码:
public class StartingHere implements Runnable {
public static void main(String[] args) {
//SECOND THREAD
try {
StartingHere sh = new StartingHere();
Thread thread = new Thread(sh);
thread.start();
//DELAYING SECOND THREAD.
Thread.currentThread().sleep(1000);
DBConnection dbConnection = new DBConnection();
} catch (Exception ex) {
System.out.println("Check db url for in DBConnection");
ex.printStackTrace();
}
}
@Override
public void run() {
//FIRST THREAD - Waiting for user to input String
String userInput = null;
Scanner scanner = new Scanner(System.in);
while(!"end".equals(userInput)) {
//Waiting for whole string
userInput = scanner.next();
}
}
}
public class DBConnection {
Connection connection;
public DBConnection() throws SQLException, ClassNotFoundException {
Class.forName("sun.jdbc.odbc.JdbcOdbcDriver");
// SECOND THREAD- Problem! Here program hangs until FIRST THREAD got some input.. why?
connection = DriverManager.getConnection("jdbc:odbc:baza");
System.out.println("DBConnection: 'Connected'");
}
}
【问题讨论】:
-
S̶e̶e̶ ̶h̶t̶t̶p̶:̶/̶/̶s̶t̶a̶c̶k̶o̶v̶e̶r̶f̶l̶o̶w̶.̶c̶o̶m̶/̶q̶u̶e̶s̶t̶i̶o̶n̶s̶/̶1̶8̶2̶8̶8̶0̶5̶8̶/̶h̶o̶w̶-̶i̶s̶-̶d̶r̶i̶v̶e̶r̶-̶c̶l̶a̶s̶s̶-̶l̶o̶c̶a̶t̶e̶d̶-̶i̶n̶-̶j̶d̶b̶c̶4̶ ̶f̶o̶r̶ ̶w̶h̶y̶ ̶t̶h̶e̶ ̶d̶r̶i̶v̶e̶r̶ ̶i̶s̶ ̶l̶o̶a̶d̶e̶d̶ ̶a̶u̶t̶o̶m̶a̶t̶i̶c̶a̶l̶l̶y̶.̶ The JDBC-ODBC driver是 JRE 的一部分,因此会自动加载。
-
我用你的例子来调用 getConnection()。
-
这很奇怪。我复制了所有代码,但它不起作用。我没有写;我认为这无关紧要,但我们开始吧:它是由 WindowsXP 上的 NetBeans 8.0 Platform JDK 1.7 构建的。一旦我在其他机器上尝试(今天不能这样做),我会在这里发布。但这将是最好的解决方案,因为我看不到连接为什么会出现死锁。谢谢你的回复!
-
我没有连接,因为我没有访问数据库的权限,但是我得到了一个异常,如果我删除了调用,
DBConnection: 'Connected'会被打印出来。也许您与数据库的连接有问题。尝试删除调用,看看是否打印了字符串。 -
不要评论/删除 DriverManager.getConnection("jdbc:odbc:baza");。因为这种方法是一种制造锁的方法。如果您可以制作虚拟 MSAcess 数据库并将其注册到 Windows ODBC 中,并为其赋予符号名称“baza”。这样 url (getConnection("jdbc:odbc:baza");) 就可以找到它。
标签: java multithreading deadlock stdin