我的问题不是特定于Java,而是我用来实现我想要的语言。
我正在尝试使用Java中的蓝牙并编写了一个简单的终端程序,即没有GUI界面可以搜索附近的蓝牙设备并列出它们。我的代码如下:
import javax.bluetooth.*;
public class BluetoothTest implements DiscoveryListener{
private static boolean isAlive = true;
public static void main(String[] args) {
try {
LocalDevice ld = LocalDevice.getLocalDevice();
if (LocalDevice.isPowerOn()){
System.out.println("Power On.");
System.out.println("Friendly Name: " + ld.getFriendlyName());
System.out.println("Address: " + ld.getBluetoothAddress());
DiscoveryAgent da = ld.getDiscoveryAgent();
da.startInquiry(DiscoveryAgent.GIAC,new BluetoothTest());
while (isAlive){
/* Sleep */
try {
Thread.sleep(200);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
} else {
System.out.println("Power Off.");
}
} catch (BluetoothStateException e) {
System.out.println(e.toString());
}
}
public void setAlive(boolean status){
isAlive = status;
}
public void deviceDiscovered(RemoteDevice rd, DeviceClass dc){
try{
System.out.println(rd.getFriendlyName(true));
} catch (java.io.IOException e){
System.out.println(e.toString());
}
}
public void inquiryCompleted(int discType){
isAlive = false;
}
public void servicesDiscovered(int transID, ServiceRecord[] sr){
}
public void serviceSearchCompleted(int transID, int respCode){
}
}
DiscoveryAgent对象的startInquiry()立即返回,并且发现的所有设备都将返回到我已实现的DiscoveryListener接口。问题是除非我包含while()循环,程序将在发现任何设备之前终止。
应用程序如何有效地驻留?它是通过一个单独的“工作”线程和一个主线程来实现的,它产生了工作线程,但它自己会一直睡到工人完成之前?
答案 0 :(得分:2)
您可以使用对象等待/通知机制来保存main方法,直到BluetoothTest通知公共对象锁。
只是一个伪代码,
定义静态最终对象_mutex = new Object();
调用startInquiry后调用_mutex.wait();这将成为主线。
在inquiryCompleted中调用_mutex.notify();这将释放主线程。
请注意,只有在startInquiry创建新线程并调用回调方法时,此代码才有效。我不太了解DiscoverAgent课程。因此,如果情况并非如此,则上述解决方案现在可以正常工作。
答案 1 :(得分:1)
Java程序将保持运行,直到所有未标记为“守护程序”的线程退出。如果Main
线程退出并且没有其他线程在运行,则程序将退出。如果你产生了另一个线程(或者如果DiscoveryAgent
正在另一个线程中运行)而不是“守护进程”线程,那么Java将一直运行直到线程退出。将循环放在main中是一种很好的方法,尽管如@jatanp所述,使用wait
/ notify
更清晰。
关于代码的一些事情:
让您的主要代码也是您的DiscoveryListener
很奇怪。我会在另一个类中隔离该功能:
public class BluetoothTest {
...
private static class OurListener implements DiscoveryListener {
}
}
isAlive
中读取,因此应将其标记为volatile
,或者您需要synchronize
围绕它。